From 5bd34b8d6f7d1736338bafbbb948565934620e72 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Mon, 13 Jul 2026 10:47:33 +0530 Subject: [PATCH 01/10] chore: update Python SDK to 22.0.0 --- CHANGELOG.md | 24 + appwrite/client.py | 13 +- appwrite/encoders/value_class_encoder.py | 26 +- appwrite/enums/billing_plan_group.py | 6 + appwrite/enums/database_status.py | 6 + appwrite/enums/health_antivirus_status.py | 6 - appwrite/enums/health_check_status.py | 5 - appwrite/enums/health_queue_name.py | 16 - appwrite/enums/o_auth2_oidc_prompt.py | 7 + appwrite/enums/o_auth_provider.py | 1 + appwrite/enums/organization_key_scopes.py | 4 + appwrite/enums/project_key_scopes.py | 8 +- appwrite/enums/project_o_auth2_oidc_prompt.py | 7 + appwrite/enums/project_o_auth_provider_id.py | 1 + appwrite/models/__init__.py | 52 +- appwrite/models/activity_event.py | 6 - appwrite/models/additional_resource.py | 30 + appwrite/models/app.py | 3 + appwrite/models/billing_plan.py | 223 +++++ appwrite/models/billing_plan_addon.py | 19 + appwrite/models/billing_plan_addon_details.py | 36 + .../billing_plan_dedicated_database_limits.py | 69 ++ appwrite/models/billing_plan_limits.py | 18 + .../models/billing_plan_supported_addons.py | 21 + appwrite/models/block.py | 3 + appwrite/models/database.py | 4 + appwrite/models/document.py | 11 + appwrite/models/health_antivirus.py | 19 - appwrite/models/health_certificate.py | 30 - appwrite/models/health_status.py | 22 - appwrite/models/health_status_list.py | 19 - appwrite/models/health_time.py | 21 - appwrite/models/locale.py | 33 + appwrite/models/log.py | 2 +- appwrite/models/o_auth2_appwrite.py | 24 + appwrite/models/o_auth2_oidc.py | 7 + appwrite/models/o_auth2_provider_list.py | 5 +- appwrite/models/oauth2_grant.py | 3 + ...health_queue.py => oauth2_organization.py} | 10 +- appwrite/models/oauth2_organization_list.py | 19 + appwrite/models/oauth2_par.py | 18 + appwrite/models/oauth2_project.py | 21 + appwrite/models/oauth2_project_list.py | 19 + appwrite/models/organization.py | 132 +++ appwrite/models/preferences.py | 11 + appwrite/models/program.py | 39 + appwrite/models/project.py | 6 + appwrite/models/row.py | 11 + appwrite/models/usage_billing_plan.py | 46 + appwrite/models/usage_data_point.py | 60 -- appwrite/models/usage_event_list.py | 19 - appwrite/models/usage_gauge_list.py | 19 - appwrite/models/usage_metric.py | 19 - appwrite/query.py | 12 + appwrite/services/account.py | 2 +- appwrite/services/apps.py | 47 + appwrite/services/backups.py | 10 +- appwrite/services/functions.py | 25 +- appwrite/services/health.py | 882 ------------------ appwrite/services/messaging.py | 197 ---- appwrite/services/oauth2.py | 290 +++++- appwrite/services/organization.py | 357 ++++++- appwrite/services/project.py | 68 +- appwrite/services/sites.py | 14 +- appwrite/services/tables_db.py | 10 +- appwrite/services/usage.py | 202 ---- appwrite/services/users.py | 2 +- .../update-labels.md} | 11 +- docs/examples/backups/create-restoration.md | 3 +- .../functions/get-deployment-download.md | 3 +- .../examples/functions/list-specifications.md | 4 +- docs/examples/health/get-antivirus.md | 16 - docs/examples/health/get-certificate.md | 18 - docs/examples/health/get-db.md | 16 - docs/examples/health/get-failed-jobs.md | 20 - docs/examples/health/get-pub-sub.md | 16 - .../examples/health/get-queue-certificates.md | 18 - docs/examples/health/get-queue-databases.md | 19 - docs/examples/health/get-queue-deletes.md | 18 - docs/examples/health/get-queue-functions.md | 18 - docs/examples/health/get-queue-logs.md | 18 - docs/examples/health/get-queue-mails.md | 18 - docs/examples/health/get-queue-messaging.md | 18 - docs/examples/health/get-queue-migrations.md | 18 - .../health/get-queue-stats-resources.md | 18 - docs/examples/health/get-queue-usage.md | 18 - docs/examples/health/get-queue-webhooks.md | 18 - docs/examples/health/get-storage-local.md | 16 - docs/examples/health/get-storage.md | 16 - docs/examples/messaging/list-provider-logs.md | 20 - .../messaging/list-subscriber-logs.md | 20 - docs/examples/messaging/list-topic-logs.md | 20 - docs/examples/oauth2/approve.md | 3 +- docs/examples/oauth2/authorize.md | 13 +- .../oauth2/create-device-authorization.md | 4 +- docs/examples/oauth2/create-par.md | 30 + docs/examples/oauth2/create-token.md | 4 +- docs/examples/oauth2/list-organizations.md | 20 + docs/examples/oauth2/list-projects.md | 20 + .../organization/create-membership.md | 23 + .../delete-membership.md} | 11 +- .../get-time.md => organization/delete.md} | 9 +- .../get-membership.md} | 10 +- .../get-cache.md => organization/get.md} | 8 +- .../list-memberships.md} | 10 +- .../update-membership.md} | 12 +- .../update.md} | 10 +- .../project/update-o-auth-2-appwrite.md | 20 + docs/examples/project/update-o-auth-2-oidc.md | 3 + .../project/update-o-auth-2-server.md | 3 +- docs/examples/sites/list-specifications.md | 4 +- docs/examples/tablesdb/create.md | 2 +- docs/examples/usage/list-events.md | 28 - docs/examples/usage/list-gauges.md | 28 - pyproject.toml | 2 +- requirements.txt | 2 +- setup.py | 4 +- test/services/test_activities.py | 4 +- test/services/test_apps.py | 42 + test/services/test_backups.py | 4 +- test/services/test_health.py | 361 ------- test/services/test_messaging.py | 60 -- test/services/test_oauth2.py | 51 +- test/services/test_organization.py | 576 ++++++++++++ test/services/test_project.py | 39 +- test/services/test_usage.py | 45 - 126 files changed, 2633 insertions(+), 2607 deletions(-) create mode 100644 appwrite/enums/billing_plan_group.py create mode 100644 appwrite/enums/database_status.py delete mode 100644 appwrite/enums/health_antivirus_status.py delete mode 100644 appwrite/enums/health_check_status.py delete mode 100644 appwrite/enums/health_queue_name.py create mode 100644 appwrite/enums/o_auth2_oidc_prompt.py create mode 100644 appwrite/enums/project_o_auth2_oidc_prompt.py create mode 100644 appwrite/models/additional_resource.py create mode 100644 appwrite/models/billing_plan.py create mode 100644 appwrite/models/billing_plan_addon.py create mode 100644 appwrite/models/billing_plan_addon_details.py create mode 100644 appwrite/models/billing_plan_dedicated_database_limits.py create mode 100644 appwrite/models/billing_plan_limits.py create mode 100644 appwrite/models/billing_plan_supported_addons.py delete mode 100644 appwrite/models/health_antivirus.py delete mode 100644 appwrite/models/health_certificate.py delete mode 100644 appwrite/models/health_status.py delete mode 100644 appwrite/models/health_status_list.py delete mode 100644 appwrite/models/health_time.py create mode 100644 appwrite/models/o_auth2_appwrite.py rename appwrite/models/{health_queue.py => oauth2_organization.py} (55%) create mode 100644 appwrite/models/oauth2_organization_list.py create mode 100644 appwrite/models/oauth2_par.py create mode 100644 appwrite/models/oauth2_project.py create mode 100644 appwrite/models/oauth2_project_list.py create mode 100644 appwrite/models/organization.py create mode 100644 appwrite/models/program.py create mode 100644 appwrite/models/usage_billing_plan.py delete mode 100644 appwrite/models/usage_data_point.py delete mode 100644 appwrite/models/usage_event_list.py delete mode 100644 appwrite/models/usage_gauge_list.py delete mode 100644 appwrite/models/usage_metric.py delete mode 100644 appwrite/services/health.py delete mode 100644 appwrite/services/usage.py rename docs/examples/{health/get-audits-db.md => apps/update-labels.md} (63%) delete mode 100644 docs/examples/health/get-antivirus.md delete mode 100644 docs/examples/health/get-certificate.md delete mode 100644 docs/examples/health/get-db.md delete mode 100644 docs/examples/health/get-failed-jobs.md delete mode 100644 docs/examples/health/get-pub-sub.md delete mode 100644 docs/examples/health/get-queue-certificates.md delete mode 100644 docs/examples/health/get-queue-databases.md delete mode 100644 docs/examples/health/get-queue-deletes.md delete mode 100644 docs/examples/health/get-queue-functions.md delete mode 100644 docs/examples/health/get-queue-logs.md delete mode 100644 docs/examples/health/get-queue-mails.md delete mode 100644 docs/examples/health/get-queue-messaging.md delete mode 100644 docs/examples/health/get-queue-migrations.md delete mode 100644 docs/examples/health/get-queue-stats-resources.md delete mode 100644 docs/examples/health/get-queue-usage.md delete mode 100644 docs/examples/health/get-queue-webhooks.md delete mode 100644 docs/examples/health/get-storage-local.md delete mode 100644 docs/examples/health/get-storage.md delete mode 100644 docs/examples/messaging/list-provider-logs.md delete mode 100644 docs/examples/messaging/list-subscriber-logs.md delete mode 100644 docs/examples/messaging/list-topic-logs.md create mode 100644 docs/examples/oauth2/create-par.md create mode 100644 docs/examples/oauth2/list-organizations.md create mode 100644 docs/examples/oauth2/list-projects.md create mode 100644 docs/examples/organization/create-membership.md rename docs/examples/{health/get.md => organization/delete-membership.md} (60%) rename docs/examples/{health/get-time.md => organization/delete.md} (60%) rename docs/examples/{health/get-queue-audits.md => organization/get-membership.md} (57%) rename docs/examples/{health/get-cache.md => organization/get.md} (59%) rename docs/examples/{messaging/list-message-logs.md => organization/list-memberships.md} (60%) rename docs/examples/{health/get-console-pausing.md => organization/update-membership.md} (55%) rename docs/examples/{health/get-queue-builds.md => organization/update.md} (56%) create mode 100644 docs/examples/project/update-o-auth-2-appwrite.md delete mode 100644 docs/examples/usage/list-events.md delete mode 100644 docs/examples/usage/list-gauges.md delete mode 100644 test/services/test_health.py delete mode 100644 test/services/test_usage.py diff --git a/CHANGELOG.md b/CHANGELOG.md index c8e7a93d..e66e10b9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,29 @@ # Change Log +## 22.0.0 + +* Breaking: removed `Health` service and all health models and enums +* Breaking: removed `Usage` service and `UsageMetric`, `UsageDataPoint`, `UsageEventList`, `UsageGaugeList` models +* Breaking: removed messaging `list_message_logs`, `list_provider_logs`, `list_subscriber_logs`, `list_topic_logs` methods +* Breaking: renamed `tables_db.create` parameter `dedicated_database_id` to `specification` +* Breaking: removed `countryCode` and `countryName` from `ActivityEvent` model +* Added: `Client.set_bearer` for OAuth access token authentication +* Added: `organization` service `get`, `update`, `delete` and membership CRUD methods +* Added: `oauth2` service `create_par`, `list_organizations`, `list_projects` methods +* Added: `resource`, `audience`, `request_uri` OAuth2 parameters; `scope` on `approve` +* Added: `appwrite` OAuth provider, `OAuth2Appwrite` model, `update_o_auth2_appwrite` method +* Added: `Query.vector_dot`, `Query.vector_cosine`, `Query.vector_euclidean` methods +* Added: `apps.update_labels` method and `labels` field on `App` model +* Added: `new_specification` parameter to `backups.create_restoration` +* Added: `type` parameter to `functions` and `sites` `list_specifications` +* Added: `token` parameter to `functions.get_deployment_download` +* Added: `prompt` and `max_age` parameters to `update_o_auth2_oidc`; `default_scopes` to `update_o_auth2_server` +* Added: `BillingPlan`, `Organization`, `Program`, `Oauth2PAR`, `DatabaseStatus`, `BillingPlanGroup` models and enums +* Added: `status` on `Database`, `mode` on `Block`, `onboarding` on `Project`, geolocation fields on `Locale` +* Added: organization, `project.oauth2`, and `stages` key scope enum values +* Fixed: booleans now serialized as `true`/`false` in flattened query parameters +* Fixed: `model_dump` on `Document`, `Row`, `Preferences` now includes dynamic `data` + ## 21.0.0 * Added: `apps` service for managing apps and app secrets diff --git a/appwrite/client.py b/appwrite/client.py index baafb0e7..83f61a8f 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -17,11 +17,11 @@ def __init__(self): self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent' : f'AppwritePythonSDK/21.0.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent' : f'AppwritePythonSDK/22.0.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '21.0.0', + 'x-sdk-version': '22.0.0', 'X-Appwrite-Response-Format' : '1.9.5', } self._config = {} @@ -67,6 +67,13 @@ def set_jwt(self, value): self._config['jwt'] = value return self + def set_bearer(self, value): + """The OAuth access token to authenticate with""" + + self._global_headers['authorization'] = value + self._config['bearer'] = value + return self + def set_locale(self, value): self._global_headers['x-appwrite-locale'] = value self._config['locale'] = value @@ -341,6 +348,8 @@ def flatten(self, data, prefix='', stringify=False): if isinstance(value, list) or isinstance(value, dict): output = {**output, **self.flatten(value, finalKey, stringify)} + elif isinstance(value, bool): + output[finalKey] = 'true' if value else 'false' else: if stringify: output[finalKey] = str(value) diff --git a/appwrite/encoders/value_class_encoder.py b/appwrite/encoders/value_class_encoder.py index 5a4914b1..b725fb9b 100644 --- a/appwrite/encoders/value_class_encoder.py +++ b/appwrite/encoders/value_class_encoder.py @@ -21,13 +21,13 @@ from ..enums.vcs_reference_type import VCSReferenceType from ..enums.deployment_download_type import DeploymentDownloadType from ..enums.execution_method import ExecutionMethod -from ..enums.health_queue_name import HealthQueueName from ..enums.message_priority import MessagePriority from ..enums.smtp_encryption import SmtpEncryption from ..enums.organization_key_scopes import OrganizationKeyScopes from ..enums.region import Region from ..enums.project_auth_method_id import ProjectAuthMethodId from ..enums.project_o_auth2_google_prompt import ProjectOAuth2GooglePrompt +from ..enums.project_o_auth2_oidc_prompt import ProjectOAuth2OidcPrompt from ..enums.project_o_auth_provider_id import ProjectOAuthProviderId from ..enums.project_policy_id import ProjectPolicyId from ..enums.project_protocol_id import ProjectProtocolId @@ -46,6 +46,7 @@ from ..enums.password_hash import PasswordHash from ..enums.messaging_provider_type import MessagingProviderType from ..enums.database_type import DatabaseType +from ..enums.database_status import DatabaseStatus from ..enums.attribute_status import AttributeStatus from ..enums.column_status import ColumnStatus from ..enums.index_status import IndexStatus @@ -53,12 +54,12 @@ from ..enums.execution_trigger import ExecutionTrigger from ..enums.execution_status import ExecutionStatus from ..enums.o_auth2_google_prompt import OAuth2GooglePrompt +from ..enums.o_auth2_oidc_prompt import OAuth2OidcPrompt from ..enums.platform_type import PlatformType -from ..enums.health_antivirus_status import HealthAntivirusStatus -from ..enums.health_check_status import HealthCheckStatus from ..enums.proxy_rule_deployment_resource_type import ProxyRuleDeploymentResourceType from ..enums.proxy_rule_status import ProxyRuleStatus from ..enums.message_status import MessageStatus +from ..enums.billing_plan_group import BillingPlanGroup class ValueClassEncoder(json.JSONEncoder): def default(self, o): @@ -128,9 +129,6 @@ def default(self, o): if isinstance(o, ExecutionMethod): return o.value - if isinstance(o, HealthQueueName): - return o.value - if isinstance(o, MessagePriority): return o.value @@ -149,6 +147,9 @@ def default(self, o): if isinstance(o, ProjectOAuth2GooglePrompt): return o.value + if isinstance(o, ProjectOAuth2OidcPrompt): + return o.value + if isinstance(o, ProjectOAuthProviderId): return o.value @@ -203,6 +204,9 @@ def default(self, o): if isinstance(o, DatabaseType): return o.value + if isinstance(o, DatabaseStatus): + return o.value + if isinstance(o, AttributeStatus): return o.value @@ -224,13 +228,10 @@ def default(self, o): if isinstance(o, OAuth2GooglePrompt): return o.value - if isinstance(o, PlatformType): - return o.value - - if isinstance(o, HealthAntivirusStatus): + if isinstance(o, OAuth2OidcPrompt): return o.value - if isinstance(o, HealthCheckStatus): + if isinstance(o, PlatformType): return o.value if isinstance(o, ProxyRuleDeploymentResourceType): @@ -242,4 +243,7 @@ def default(self, o): if isinstance(o, MessageStatus): return o.value + if isinstance(o, BillingPlanGroup): + return o.value + return super().default(o) diff --git a/appwrite/enums/billing_plan_group.py b/appwrite/enums/billing_plan_group.py new file mode 100644 index 00000000..5a659196 --- /dev/null +++ b/appwrite/enums/billing_plan_group.py @@ -0,0 +1,6 @@ +from enum import Enum + +class BillingPlanGroup(Enum): + STARTER = "starter" + PRO = "pro" + SCALE = "scale" diff --git a/appwrite/enums/database_status.py b/appwrite/enums/database_status.py new file mode 100644 index 00000000..7c5f888f --- /dev/null +++ b/appwrite/enums/database_status.py @@ -0,0 +1,6 @@ +from enum import Enum + +class DatabaseStatus(Enum): + PROVISIONING = "provisioning" + READY = "ready" + FAILED = "failed" diff --git a/appwrite/enums/health_antivirus_status.py b/appwrite/enums/health_antivirus_status.py deleted file mode 100644 index 38c1684b..00000000 --- a/appwrite/enums/health_antivirus_status.py +++ /dev/null @@ -1,6 +0,0 @@ -from enum import Enum - -class HealthAntivirusStatus(Enum): - DISABLED = "disabled" - OFFLINE = "offline" - ONLINE = "online" diff --git a/appwrite/enums/health_check_status.py b/appwrite/enums/health_check_status.py deleted file mode 100644 index 2cc9c113..00000000 --- a/appwrite/enums/health_check_status.py +++ /dev/null @@ -1,5 +0,0 @@ -from enum import Enum - -class HealthCheckStatus(Enum): - PASS = "pass" - FAIL = "fail" diff --git a/appwrite/enums/health_queue_name.py b/appwrite/enums/health_queue_name.py deleted file mode 100644 index a04ab15f..00000000 --- a/appwrite/enums/health_queue_name.py +++ /dev/null @@ -1,16 +0,0 @@ -from enum import Enum - -class HealthQueueName(Enum): - V1_DATABASE = "v1-database" - V1_DELETES = "v1-deletes" - V1_AUDITS = "v1-audits" - V1_MAILS = "v1-mails" - V1_FUNCTIONS = "v1-functions" - V1_STATS_RESOURCES = "v1-stats-resources" - V1_STATS_USAGE = "v1-stats-usage" - V1_WEBHOOKS = "v1-webhooks" - V1_CERTIFICATES = "v1-certificates" - V1_BUILDS = "v1-builds" - V1_SCREENSHOTS = "v1-screenshots" - V1_MESSAGING = "v1-messaging" - V1_MIGRATIONS = "v1-migrations" diff --git a/appwrite/enums/o_auth2_oidc_prompt.py b/appwrite/enums/o_auth2_oidc_prompt.py new file mode 100644 index 00000000..0c21c203 --- /dev/null +++ b/appwrite/enums/o_auth2_oidc_prompt.py @@ -0,0 +1,7 @@ +from enum import Enum + +class OAuth2OidcPrompt(Enum): + NONE = "none" + LOGIN = "login" + CONSENT = "consent" + SELECT_ACCOUNT = "select_account" diff --git a/appwrite/enums/o_auth_provider.py b/appwrite/enums/o_auth_provider.py index 18b69a49..e0aa4ea5 100644 --- a/appwrite/enums/o_auth_provider.py +++ b/appwrite/enums/o_auth_provider.py @@ -3,6 +3,7 @@ class OAuthProvider(Enum): AMAZON = "amazon" APPLE = "apple" + APPWRITE = "appwrite" AUTH0 = "auth0" AUTHENTIK = "authentik" AUTODESK = "autodesk" diff --git a/appwrite/enums/organization_key_scopes.py b/appwrite/enums/organization_key_scopes.py index aa788f1a..ab4e4526 100644 --- a/appwrite/enums/organization_key_scopes.py +++ b/appwrite/enums/organization_key_scopes.py @@ -7,6 +7,10 @@ class OrganizationKeyScopes(Enum): DEVKEYS_WRITE = "devKeys.write" ORGANIZATION_KEYS_READ = "organization.keys.read" ORGANIZATION_KEYS_WRITE = "organization.keys.write" + ORGANIZATION_MEMBERSHIPS_READ = "organization.memberships.read" + ORGANIZATION_MEMBERSHIPS_WRITE = "organization.memberships.write" + ORGANIZATION_READ = "organization.read" + ORGANIZATION_WRITE = "organization.write" DOMAINS_READ = "domains.read" DOMAINS_WRITE = "domains.write" KEYS_READ = "keys.read" diff --git a/appwrite/enums/project_key_scopes.py b/appwrite/enums/project_key_scopes.py index a0356058..10099119 100644 --- a/appwrite/enums/project_key_scopes.py +++ b/appwrite/enums/project_key_scopes.py @@ -13,10 +13,12 @@ class ProjectKeyScopes(Enum): POLICIES_WRITE = "policies.write" PROJECT_POLICIES_READ = "project.policies.read" PROJECT_POLICIES_WRITE = "project.policies.write" + PROJECT_OAUTH2_READ = "project.oauth2.read" + PROJECT_OAUTH2_WRITE = "project.oauth2.write" TEMPLATES_READ = "templates.read" TEMPLATES_WRITE = "templates.write" - OAUTH2_READ = "oauth2.read" - OAUTH2_WRITE = "oauth2.write" + STAGES_READ = "stages.read" + STAGES_WRITE = "stages.write" USERS_READ = "users.read" USERS_WRITE = "users.write" SESSIONS_READ = "sessions.read" @@ -97,4 +99,6 @@ class ProjectKeyScopes(Enum): EVENTS_READ = "events.read" APPS_READ = "apps.read" APPS_WRITE = "apps.write" + OAUTH2_READ = "oauth2.read" + OAUTH2_WRITE = "oauth2.write" USAGE_READ = "usage.read" diff --git a/appwrite/enums/project_o_auth2_oidc_prompt.py b/appwrite/enums/project_o_auth2_oidc_prompt.py new file mode 100644 index 00000000..43c64713 --- /dev/null +++ b/appwrite/enums/project_o_auth2_oidc_prompt.py @@ -0,0 +1,7 @@ +from enum import Enum + +class ProjectOAuth2OidcPrompt(Enum): + NONE = "none" + LOGIN = "login" + CONSENT = "consent" + SELECT_ACCOUNT = "select_account" diff --git a/appwrite/enums/project_o_auth_provider_id.py b/appwrite/enums/project_o_auth_provider_id.py index 71ba1213..c61f6002 100644 --- a/appwrite/enums/project_o_auth_provider_id.py +++ b/appwrite/enums/project_o_auth_provider_id.py @@ -3,6 +3,7 @@ class ProjectOAuthProviderId(Enum): AMAZON = "amazon" APPLE = "apple" + APPWRITE = "appwrite" AUTH0 = "auth0" AUTHENTIK = "authentik" AUTODESK = "autodesk" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index e8267dd9..8e75504a 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -34,7 +34,6 @@ from .mock_number_list import MockNumberList from .policy_list import PolicyList from .email_template_list import EmailTemplateList -from .health_status_list import HealthStatusList from .proxy_rule_list import ProxyRuleList from .locale_code_list import LocaleCodeList from .provider_list import ProviderList @@ -160,6 +159,7 @@ from .o_auth2_tradeshift import OAuth2Tradeshift from .o_auth2_paypal import OAuth2Paypal from .o_auth2_gitlab import OAuth2Gitlab +from .o_auth2_appwrite import OAuth2Appwrite from .o_auth2_authentik import OAuth2Authentik from .o_auth2_auth0 import OAuth2Auth0 from .o_auth2_fusion_auth import OAuth2FusionAuth @@ -192,11 +192,6 @@ from .language import Language from .currency import Currency from .phone import Phone -from .health_antivirus import HealthAntivirus -from .health_queue import HealthQueue -from .health_status import HealthStatus -from .health_certificate import HealthCertificate -from .health_time import HealthTime from .headers import Headers from .specification import Specification from .proxy_rule import ProxyRule @@ -215,19 +210,25 @@ from .insight_cta import InsightCTA from .report import Report from .activity_event import ActivityEvent +from .additional_resource import AdditionalResource from .backup_archive import BackupArchive from .billing_limits import BillingLimits +from .billing_plan import BillingPlan +from .billing_plan_addon import BillingPlanAddon +from .billing_plan_addon_details import BillingPlanAddonDetails +from .billing_plan_limits import BillingPlanLimits +from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits +from .billing_plan_supported_addons import BillingPlanSupportedAddons from .block import Block +from .organization import Organization from .backup_policy import BackupPolicy from .policy_deny_aliased_email import PolicyDenyAliasedEmail from .policy_deny_disposable_email import PolicyDenyDisposableEmail from .policy_deny_free_email import PolicyDenyFreeEmail from .policy_deny_corporate_email import PolicyDenyCorporateEmail +from .program import Program from .backup_restoration import BackupRestoration -from .usage_data_point import UsageDataPoint -from .usage_event_list import UsageEventList -from .usage_gauge_list import UsageGaugeList -from .usage_metric import UsageMetric +from .usage_billing_plan import UsageBillingPlan from .app import App from .app_secret import AppSecret from .app_secret_plaintext import AppSecretPlaintext @@ -236,7 +237,12 @@ from .oauth2_reject import Oauth2Reject from .oauth2_grant import Oauth2Grant from .oauth2_device_authorization import Oauth2DeviceAuthorization +from .oauth2_par import Oauth2PAR from .oauth2_token import Oauth2Token +from .oauth2_project import Oauth2Project +from .oauth2_organization import Oauth2Organization +from .oauth2_project_list import Oauth2ProjectList +from .oauth2_organization_list import Oauth2OrganizationList from .activity_event_list import ActivityEventList from .backup_archive_list import BackupArchiveList from .backup_policy_list import BackupPolicyList @@ -281,7 +287,6 @@ 'MockNumberList', 'PolicyList', 'EmailTemplateList', - 'HealthStatusList', 'ProxyRuleList', 'LocaleCodeList', 'ProviderList', @@ -407,6 +412,7 @@ 'OAuth2Tradeshift', 'OAuth2Paypal', 'OAuth2Gitlab', + 'OAuth2Appwrite', 'OAuth2Authentik', 'OAuth2Auth0', 'OAuth2FusionAuth', @@ -439,11 +445,6 @@ 'Language', 'Currency', 'Phone', - 'HealthAntivirus', - 'HealthQueue', - 'HealthStatus', - 'HealthCertificate', - 'HealthTime', 'Headers', 'Specification', 'ProxyRule', @@ -462,19 +463,25 @@ 'InsightCTA', 'Report', 'ActivityEvent', + 'AdditionalResource', 'BackupArchive', 'BillingLimits', + 'BillingPlan', + 'BillingPlanAddon', + 'BillingPlanAddonDetails', + 'BillingPlanLimits', + 'BillingPlanDedicatedDatabaseLimits', + 'BillingPlanSupportedAddons', 'Block', + 'Organization', 'BackupPolicy', 'PolicyDenyAliasedEmail', 'PolicyDenyDisposableEmail', 'PolicyDenyFreeEmail', 'PolicyDenyCorporateEmail', + 'Program', 'BackupRestoration', - 'UsageDataPoint', - 'UsageEventList', - 'UsageGaugeList', - 'UsageMetric', + 'UsageBillingPlan', 'App', 'AppSecret', 'AppSecretPlaintext', @@ -483,7 +490,12 @@ 'Oauth2Reject', 'Oauth2Grant', 'Oauth2DeviceAuthorization', + 'Oauth2PAR', 'Oauth2Token', + 'Oauth2Project', + 'Oauth2Organization', + 'Oauth2ProjectList', + 'Oauth2OrganizationList', 'ActivityEventList', 'BackupArchiveList', 'BackupPolicyList', diff --git a/appwrite/models/activity_event.py b/appwrite/models/activity_event.py index 9e2b6313..11265c1d 100644 --- a/appwrite/models/activity_event.py +++ b/appwrite/models/activity_event.py @@ -45,10 +45,6 @@ class ActivityEvent(AppwriteModel): Team ID. hostname : str Hostname. - countrycode : str - Country two-character ISO 3166-1 alpha code. - countryname : str - Country name. """ id: str = Field(..., alias='$id') actortype: str = Field(..., alias='actorType') @@ -68,5 +64,3 @@ class ActivityEvent(AppwriteModel): projectid: str = Field(..., alias='projectId') teamid: str = Field(..., alias='teamId') hostname: str = Field(..., alias='hostname') - countrycode: str = Field(..., alias='countryCode') - countryname: str = Field(..., alias='countryName') diff --git a/appwrite/models/additional_resource.py b/appwrite/models/additional_resource.py new file mode 100644 index 00000000..63e01170 --- /dev/null +++ b/appwrite/models/additional_resource.py @@ -0,0 +1,30 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class AdditionalResource(AppwriteModel): + """ + AdditionalResource + + Attributes + ---------- + name : str + Resource name + unit : str + Resource unit + currency : str + Price currency + price : float + Price + value : float + Resource value + invoicedesc : str + Description on invoice + """ + name: str = Field(..., alias='name') + unit: str = Field(..., alias='unit') + currency: str = Field(..., alias='currency') + price: float = Field(..., alias='price') + value: float = Field(..., alias='value') + invoicedesc: str = Field(..., alias='invoiceDesc') diff --git a/appwrite/models/app.py b/appwrite/models/app.py index 189910d2..f570a66c 100644 --- a/appwrite/models/app.py +++ b/appwrite/models/app.py @@ -34,6 +34,8 @@ class App(AppwriteModel): Application tagline shown to users during OAuth2 consent. tags : List[Any] Application tags shown to users during OAuth2 consent. + labels : List[Any] + Application labels. Read-only for clients; only a server SDK using a project API key can update them. images : List[Any] Application image URLs shown to users during OAuth2 consent. supporturl : str @@ -69,6 +71,7 @@ class App(AppwriteModel): contacts: List[Any] = Field(..., alias='contacts') tagline: str = Field(..., alias='tagline') tags: List[Any] = Field(..., alias='tags') + labels: List[Any] = Field(..., alias='labels') images: List[Any] = Field(..., alias='images') supporturl: str = Field(..., alias='supportUrl') datadeletionurl: str = Field(..., alias='dataDeletionUrl') diff --git a/appwrite/models/billing_plan.py b/appwrite/models/billing_plan.py new file mode 100644 index 00000000..64db521b --- /dev/null +++ b/appwrite/models/billing_plan.py @@ -0,0 +1,223 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .usage_billing_plan import UsageBillingPlan +from .billing_plan_addon import BillingPlanAddon +from .billing_plan_supported_addons import BillingPlanSupportedAddons +from .billing_plan_limits import BillingPlanLimits +from ..enums.billing_plan_group import BillingPlanGroup +from .program import Program +from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits + +class BillingPlan(AppwriteModel): + """ + billingPlan + + Attributes + ---------- + id : str + Plan ID. + name : str + Plan name + desc : str + Plan description + order : float + Plan order + price : float + Price + trial : float + Trial days + bandwidth : float + Bandwidth + storage : float + Storage + imagetransformations : float + Image Transformations + screenshotsgenerated : float + Screenshots generated + members : float + Members + webhooks : float + Webhooks + projects : float + Projects + platforms : float + Platforms + users : float + Users + teams : float + Teams + databases : float + Databases + databasesreads : float + Database reads per month + databaseswrites : float + Database writes per month + databasesbatchsize : float + Database batch size limit + buckets : float + Buckets + filesize : float + File size + functions : float + Functions + sites : float + Sites + executions : float + Function executions + executionsretentioncount : float + Rolling max executions retained per function/site + gbhours : float + GB hours for functions + realtime : float + Realtime connections + realtimemessages : float + Realtime messages + messages : float + Messages per month + topics : float + Topics for messaging + authphone : float + SMS authentications per month + domains : float + Custom domains + activitylogs : float + Activity log days + usagelogs : float + Usage history days + usagelogsintervals : Optional[List[Any]] + Usage log time intervals allowed for this plan (e.g. 15m, 1h, 1d). + projectinactivitydays : float + Number of days of console inactivity before a project is paused. 0 means pausing is disabled. + alertlimit : float + Alert threshold percentage + usage : UsageBillingPlan + Additional resources + addons : BillingPlanAddon + Addons + budgetcapenabled : bool + Budget cap enabled or disabled. + customsmtp : bool + Custom SMTP + emailbranding : bool + Appwrite branding in email + requirespaymentmethod : bool + Does plan require payment method + requiresbillingaddress : bool + Does plan require billing address + isavailable : bool + Is the billing plan available + selfservice : bool + Can user change the plan themselves + premiumsupport : bool + Does plan enable premium support + budgeting : bool + Does plan support budget cap + supportsmocknumbers : bool + Does plan support mock numbers + supportsorganizationroles : bool + Does plan support organization roles + supportscredits : bool + Does plan support credit + supportsdisposableemailvalidation : bool + Does plan support blocking disposable email addresses. + supportscanonicalemailvalidation : bool + Does plan support requiring canonical email addresses. + supportsfreeemailvalidation : bool + Does plan support blocking free email addresses. + supportscorporateemailvalidation : bool + Does plan support restricting sign-ups to corporate email addresses only. + supportsprojectspecificroles : bool + Does plan support project-specific member roles. + backupsenabled : bool + Does plan support backup policies. + usageperproject : bool + Whether usage addons are calculated per project. + supportedaddons : BillingPlanSupportedAddons + Supported addons for this plan + backuppolicies : float + How many policies does plan support + deploymentsize : float + Maximum function and site deployment size in MB + buildsize : float + Maximum function and site deployment size in MB + databasesallowencrypt : bool + Does the plan support encrypted string attributes or not. + limits : Optional[BillingPlanLimits] + Plan specific limits + group : BillingPlanGroup + Group of this billing plan for variants + program : Optional[Program] + Details of the program this plan is a part of. + dedicateddatabases : Optional[BillingPlanDedicatedDatabaseLimits] + Dedicated database limits available to this plan. + """ + id: str = Field(..., alias='$id') + name: str = Field(..., alias='name') + desc: str = Field(..., alias='desc') + order: float = Field(..., alias='order') + price: float = Field(..., alias='price') + trial: float = Field(..., alias='trial') + bandwidth: float = Field(..., alias='bandwidth') + storage: float = Field(..., alias='storage') + imagetransformations: float = Field(..., alias='imageTransformations') + screenshotsgenerated: float = Field(..., alias='screenshotsGenerated') + members: float = Field(..., alias='members') + webhooks: float = Field(..., alias='webhooks') + projects: float = Field(..., alias='projects') + platforms: float = Field(..., alias='platforms') + users: float = Field(..., alias='users') + teams: float = Field(..., alias='teams') + databases: float = Field(..., alias='databases') + databasesreads: float = Field(..., alias='databasesReads') + databaseswrites: float = Field(..., alias='databasesWrites') + databasesbatchsize: float = Field(..., alias='databasesBatchSize') + buckets: float = Field(..., alias='buckets') + filesize: float = Field(..., alias='fileSize') + functions: float = Field(..., alias='functions') + sites: float = Field(..., alias='sites') + executions: float = Field(..., alias='executions') + executionsretentioncount: float = Field(..., alias='executionsRetentionCount') + gbhours: float = Field(..., alias='GBHours') + realtime: float = Field(..., alias='realtime') + realtimemessages: float = Field(..., alias='realtimeMessages') + messages: float = Field(..., alias='messages') + topics: float = Field(..., alias='topics') + authphone: float = Field(..., alias='authPhone') + domains: float = Field(..., alias='domains') + activitylogs: float = Field(..., alias='activityLogs') + usagelogs: float = Field(..., alias='usageLogs') + usagelogsintervals: Optional[List[Any]] = Field(default=None, alias='usageLogsIntervals') + projectinactivitydays: float = Field(..., alias='projectInactivityDays') + alertlimit: float = Field(..., alias='alertLimit') + usage: UsageBillingPlan = Field(..., alias='usage') + addons: BillingPlanAddon = Field(..., alias='addons') + budgetcapenabled: bool = Field(..., alias='budgetCapEnabled') + customsmtp: bool = Field(..., alias='customSmtp') + emailbranding: bool = Field(..., alias='emailBranding') + requirespaymentmethod: bool = Field(..., alias='requiresPaymentMethod') + requiresbillingaddress: bool = Field(..., alias='requiresBillingAddress') + isavailable: bool = Field(..., alias='isAvailable') + selfservice: bool = Field(..., alias='selfService') + premiumsupport: bool = Field(..., alias='premiumSupport') + budgeting: bool = Field(..., alias='budgeting') + supportsmocknumbers: bool = Field(..., alias='supportsMockNumbers') + supportsorganizationroles: bool = Field(..., alias='supportsOrganizationRoles') + supportscredits: bool = Field(..., alias='supportsCredits') + supportsdisposableemailvalidation: bool = Field(..., alias='supportsDisposableEmailValidation') + supportscanonicalemailvalidation: bool = Field(..., alias='supportsCanonicalEmailValidation') + supportsfreeemailvalidation: bool = Field(..., alias='supportsFreeEmailValidation') + supportscorporateemailvalidation: bool = Field(..., alias='supportsCorporateEmailValidation') + supportsprojectspecificroles: bool = Field(..., alias='supportsProjectSpecificRoles') + backupsenabled: bool = Field(..., alias='backupsEnabled') + usageperproject: bool = Field(..., alias='usagePerProject') + supportedaddons: BillingPlanSupportedAddons = Field(..., alias='supportedAddons') + backuppolicies: float = Field(..., alias='backupPolicies') + deploymentsize: float = Field(..., alias='deploymentSize') + buildsize: float = Field(..., alias='buildSize') + databasesallowencrypt: bool = Field(..., alias='databasesAllowEncrypt') + limits: Optional[BillingPlanLimits] = Field(default=None, alias='limits') + group: BillingPlanGroup = Field(..., alias='group') + program: Optional[Program] = Field(default=None, alias='program') + dedicateddatabases: Optional[BillingPlanDedicatedDatabaseLimits] = Field(default=None, alias='dedicatedDatabases') diff --git a/appwrite/models/billing_plan_addon.py b/appwrite/models/billing_plan_addon.py new file mode 100644 index 00000000..b1d75b34 --- /dev/null +++ b/appwrite/models/billing_plan_addon.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .billing_plan_addon_details import BillingPlanAddonDetails + +class BillingPlanAddon(AppwriteModel): + """ + Addon + + Attributes + ---------- + seats : BillingPlanAddonDetails + Addon seats + projects : BillingPlanAddonDetails + Addon projects + """ + seats: BillingPlanAddonDetails = Field(..., alias='seats') + projects: BillingPlanAddonDetails = Field(..., alias='projects') diff --git a/appwrite/models/billing_plan_addon_details.py b/appwrite/models/billing_plan_addon_details.py new file mode 100644 index 00000000..8acd360c --- /dev/null +++ b/appwrite/models/billing_plan_addon_details.py @@ -0,0 +1,36 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class BillingPlanAddonDetails(AppwriteModel): + """ + Details + + Attributes + ---------- + supported : bool + Is the addon supported in the plan? + planincluded : float + Addon plan included value + limit : float + Addon limit + type : str + Addon type + currency : str + Price currency + price : float + Price + value : float + Resource value + invoicedesc : str + Description on invoice + """ + supported: bool = Field(..., alias='supported') + planincluded: float = Field(..., alias='planIncluded') + limit: float = Field(..., alias='limit') + type: str = Field(..., alias='type') + currency: str = Field(..., alias='currency') + price: float = Field(..., alias='price') + value: float = Field(..., alias='value') + invoicedesc: str = Field(..., alias='invoiceDesc') diff --git a/appwrite/models/billing_plan_dedicated_database_limits.py b/appwrite/models/billing_plan_dedicated_database_limits.py new file mode 100644 index 00000000..754c1666 --- /dev/null +++ b/appwrite/models/billing_plan_dedicated_database_limits.py @@ -0,0 +1,69 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class BillingPlanDedicatedDatabaseLimits(AppwriteModel): + """ + dedicatedDatabaseLimits + + Attributes + ---------- + mincpu : Optional[float] + Minimum CPU allocation in millicores. + maxcpu : Optional[float] + Maximum CPU allocation in millicores. + minmemorymb : Optional[float] + Minimum memory allocation in megabytes. + maxmemorymb : Optional[float] + Maximum memory allocation in megabytes. + minstoragegb : Optional[float] + Minimum storage allocation in gigabytes. + maxstoragegb : Optional[float] + Maximum storage allocation in gigabytes. + maxreplicas : Optional[float] + Maximum number of high-availability replicas per dedicated database. + maxconnections : Optional[float] + Maximum number of client connections. + maxipallowlistsize : Optional[float] + Maximum number of entries allowed in the IP allowlist. + maxextensions : Optional[float] + Maximum number of database extensions that can be enabled. + maxbackupretentiondays : Optional[float] + Maximum number of days a backup can be retained. + maxpitrretentiondays : Optional[float] + Maximum number of days of point-in-time recovery data that can be retained. + maxsqlapimaxrows : Optional[float] + Maximum number of rows a single SQL API query can return. + maxsqlapimaxbytes : Optional[float] + Maximum response size in bytes for a single SQL API query. + maxsqlapitimeoutseconds : Optional[float] + Maximum execution time in seconds for a single SQL API query. + maxsqlapiallowedstatements : Optional[float] + Maximum number of SQL statement types that can be permitted through the SQL API. + allowedsqlstatements : Optional[List[Any]] + SQL statement types permitted through the SQL API. + allowedstorageclasses : Optional[List[Any]] + Storage classes available for dedicated databases. + allowedsyncmodes : Optional[List[Any]] + Replica synchronization modes available for dedicated databases. + """ + mincpu: Optional[float] = Field(default=None, alias='minCpu') + maxcpu: Optional[float] = Field(default=None, alias='maxCpu') + minmemorymb: Optional[float] = Field(default=None, alias='minMemoryMb') + maxmemorymb: Optional[float] = Field(default=None, alias='maxMemoryMb') + minstoragegb: Optional[float] = Field(default=None, alias='minStorageGb') + maxstoragegb: Optional[float] = Field(default=None, alias='maxStorageGb') + maxreplicas: Optional[float] = Field(default=None, alias='maxReplicas') + maxconnections: Optional[float] = Field(default=None, alias='maxConnections') + maxipallowlistsize: Optional[float] = Field(default=None, alias='maxIpAllowlistSize') + maxextensions: Optional[float] = Field(default=None, alias='maxExtensions') + maxbackupretentiondays: Optional[float] = Field(default=None, alias='maxBackupRetentionDays') + maxpitrretentiondays: Optional[float] = Field(default=None, alias='maxPitrRetentionDays') + maxsqlapimaxrows: Optional[float] = Field(default=None, alias='maxSqlApiMaxRows') + maxsqlapimaxbytes: Optional[float] = Field(default=None, alias='maxSqlApiMaxBytes') + maxsqlapitimeoutseconds: Optional[float] = Field(default=None, alias='maxSqlApiTimeoutSeconds') + maxsqlapiallowedstatements: Optional[float] = Field(default=None, alias='maxSqlApiAllowedStatements') + allowedsqlstatements: Optional[List[Any]] = Field(default=None, alias='allowedSqlStatements') + allowedstorageclasses: Optional[List[Any]] = Field(default=None, alias='allowedStorageClasses') + allowedsyncmodes: Optional[List[Any]] = Field(default=None, alias='allowedSyncModes') diff --git a/appwrite/models/billing_plan_limits.py b/appwrite/models/billing_plan_limits.py new file mode 100644 index 00000000..4a5abbd9 --- /dev/null +++ b/appwrite/models/billing_plan_limits.py @@ -0,0 +1,18 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class BillingPlanLimits(AppwriteModel): + """ + PlanLimits + + Attributes + ---------- + credits : Optional[float] + Credits limit per billing cycle + dailycredits : Optional[float] + Daily credits limit (if applicable) + """ + credits: Optional[float] = Field(default=None, alias='credits') + dailycredits: Optional[float] = Field(default=None, alias='dailyCredits') diff --git a/appwrite/models/billing_plan_supported_addons.py b/appwrite/models/billing_plan_supported_addons.py new file mode 100644 index 00000000..be64dde3 --- /dev/null +++ b/appwrite/models/billing_plan_supported_addons.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class BillingPlanSupportedAddons(AppwriteModel): + """ + BillingPlanSupportedAddons + + Attributes + ---------- + baa : bool + Whether the plan supports BAA (Business Associate Agreement) addon + premiumgeodb : bool + Whether the plan supports Premium Geo DB addon (project-level) + premiumgeodborg : bool + Whether the plan supports Premium Geo DB addon (organization-level) + """ + baa: bool = Field(..., alias='baa') + premiumgeodb: bool = Field(..., alias='premiumGeoDB') + premiumgeodborg: bool = Field(..., alias='premiumGeoDBOrg') diff --git a/appwrite/models/block.py b/appwrite/models/block.py index 4e11336d..95ba2075 100644 --- a/appwrite/models/block.py +++ b/appwrite/models/block.py @@ -15,6 +15,8 @@ class Block(AppwriteModel): Resource type that is blocked resourceid : str Resource identifier that is blocked + mode : str + Block mode. full blocks reads and writes; readOnly blocks writes only. reason : Optional[str] Reason for the block. Can be null if no reason was provided. expiredat : Optional[str] @@ -33,6 +35,7 @@ class Block(AppwriteModel): createdat: str = Field(..., alias='$createdAt') resourcetype: str = Field(..., alias='resourceType') resourceid: str = Field(..., alias='resourceId') + mode: str = Field(..., alias='mode') reason: Optional[str] = Field(default=None, alias='reason') expiredat: Optional[str] = Field(default=None, alias='expiredAt') projectname: str = Field(..., alias='projectName') diff --git a/appwrite/models/database.py b/appwrite/models/database.py index 784fc2a7..b491a89a 100644 --- a/appwrite/models/database.py +++ b/appwrite/models/database.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel from ..enums.database_type import DatabaseType +from ..enums.database_status import DatabaseStatus from .backup_policy import BackupPolicy from .backup_archive import BackupArchive @@ -24,6 +25,8 @@ class Database(AppwriteModel): If database is enabled. Can be 'enabled' or 'disabled'. When disabled, the database is inaccessible to users, but remains accessible to Server SDKs using API keys. type : DatabaseType Database type. + status : Optional[DatabaseStatus] + Database status. Possible values: `provisioning`, `ready` or `failed` policies : List[BackupPolicy] Database backup policies. archives : List[BackupArchive] @@ -35,5 +38,6 @@ class Database(AppwriteModel): updatedat: str = Field(..., alias='$updatedAt') enabled: bool = Field(..., alias='enabled') type: DatabaseType = Field(..., alias='type') + status: Optional[DatabaseStatus] = Field(default=None, alias='status') policies: List[BackupPolicy] = Field(..., alias='policies') archives: List[BackupArchive] = Field(..., alias='archives') diff --git a/appwrite/models/document.py b/appwrite/models/document.py index dcff339a..4df880fc 100644 --- a/appwrite/models/document.py +++ b/appwrite/models/document.py @@ -57,6 +57,17 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) + def model_dump(self, **kwargs) -> Dict[str, Any]: + result = super().model_dump(**kwargs) + if hasattr(self, '_data'): + if isinstance(self._data, dict): + result['data'] = self._data + elif hasattr(self._data, 'model_dump'): + result['data'] = self._data.model_dump(**kwargs) + else: + result['data'] = self._data + return result + def to_dict(self) -> Dict[str, Any]: result = super().to_dict() if hasattr(self, '_data'): diff --git a/appwrite/models/health_antivirus.py b/appwrite/models/health_antivirus.py deleted file mode 100644 index 4e15043d..00000000 --- a/appwrite/models/health_antivirus.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from ..enums.health_antivirus_status import HealthAntivirusStatus - -class HealthAntivirus(AppwriteModel): - """ - Health Antivirus - - Attributes - ---------- - version : str - Antivirus version. - status : HealthAntivirusStatus - Antivirus status. Possible values are: `disabled`, `offline`, `online` - """ - version: str = Field(..., alias='version') - status: HealthAntivirusStatus = Field(..., alias='status') diff --git a/appwrite/models/health_certificate.py b/appwrite/models/health_certificate.py deleted file mode 100644 index 58999e72..00000000 --- a/appwrite/models/health_certificate.py +++ /dev/null @@ -1,30 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel - -class HealthCertificate(AppwriteModel): - """ - Health Certificate - - Attributes - ---------- - name : str - Certificate name - subjectsn : str - Subject SN - issuerorganisation : str - Issuer organisation - validfrom : str - Valid from - validto : str - Valid to - signaturetypesn : str - Signature type SN - """ - name: str = Field(..., alias='name') - subjectsn: str = Field(..., alias='subjectSN') - issuerorganisation: str = Field(..., alias='issuerOrganisation') - validfrom: str = Field(..., alias='validFrom') - validto: str = Field(..., alias='validTo') - signaturetypesn: str = Field(..., alias='signatureTypeSN') diff --git a/appwrite/models/health_status.py b/appwrite/models/health_status.py deleted file mode 100644 index 0ae11466..00000000 --- a/appwrite/models/health_status.py +++ /dev/null @@ -1,22 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from ..enums.health_check_status import HealthCheckStatus - -class HealthStatus(AppwriteModel): - """ - Health Status - - Attributes - ---------- - name : str - Name of the service. - ping : float - Duration in milliseconds how long the health check took. - status : HealthCheckStatus - Service status. Possible values are: `pass`, `fail` - """ - name: str = Field(..., alias='name') - ping: float = Field(..., alias='ping') - status: HealthCheckStatus = Field(..., alias='status') diff --git a/appwrite/models/health_status_list.py b/appwrite/models/health_status_list.py deleted file mode 100644 index 26904371..00000000 --- a/appwrite/models/health_status_list.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from .health_status import HealthStatus - -class HealthStatusList(AppwriteModel): - """ - Status List - - Attributes - ---------- - total : float - Total number of statuses that matched your query. - statuses : List[HealthStatus] - List of statuses. - """ - total: float = Field(..., alias='total') - statuses: List[HealthStatus] = Field(..., alias='statuses') diff --git a/appwrite/models/health_time.py b/appwrite/models/health_time.py deleted file mode 100644 index 240694d9..00000000 --- a/appwrite/models/health_time.py +++ /dev/null @@ -1,21 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel - -class HealthTime(AppwriteModel): - """ - Health Time - - Attributes - ---------- - remotetime : float - Current unix timestamp on trustful remote server. - localtime : float - Current unix timestamp of local server where Appwrite runs. - diff : float - Difference of unix remote and local timestamps in milliseconds. - """ - remotetime: float = Field(..., alias='remoteTime') - localtime: float = Field(..., alias='localTime') - diff: float = Field(..., alias='diff') diff --git a/appwrite/models/locale.py b/appwrite/models/locale.py index 95952e14..f8aa6de8 100644 --- a/appwrite/models/locale.py +++ b/appwrite/models/locale.py @@ -23,6 +23,28 @@ class Locale(AppwriteModel): True if country is part of the European Union. currency : str Currency code in [ISO 4217-1](http://en.wikipedia.org/wiki/ISO_4217) three-character format + city : Optional[str] + City + timezone : Optional[str] + Name of timezone + postalcode : Optional[str] + Postal code + latitude : Optional[float] + Latitude + longitude : Optional[float] + Longitude + autonomoussystemnumber : Optional[str] + Autonomous System Number (ASN) of the IP + autonomoussystemorganization : Optional[str] + Organization that owns the ASN + isp : Optional[str] + Internet service provider of the IP + connectiontype : Optional[str] + Connection type of the IP (e.g. cable, cellular, corporate) + connectionusagetype : Optional[str] + User type classification of the IP (e.g. residential, business, hosting) + connectionorganization : Optional[str] + Registered organization of the IP """ ip: str = Field(..., alias='ip') countrycode: str = Field(..., alias='countryCode') @@ -31,3 +53,14 @@ class Locale(AppwriteModel): continent: str = Field(..., alias='continent') eu: bool = Field(..., alias='eu') currency: str = Field(..., alias='currency') + city: Optional[str] = Field(default=None, alias='city') + timezone: Optional[str] = Field(default=None, alias='timeZone') + postalcode: Optional[str] = Field(default=None, alias='postalCode') + latitude: Optional[float] = Field(default=None, alias='latitude') + longitude: Optional[float] = Field(default=None, alias='longitude') + autonomoussystemnumber: Optional[str] = Field(default=None, alias='autonomousSystemNumber') + autonomoussystemorganization: Optional[str] = Field(default=None, alias='autonomousSystemOrganization') + isp: Optional[str] = Field(default=None, alias='isp') + connectiontype: Optional[str] = Field(default=None, alias='connectionType') + connectionusagetype: Optional[str] = Field(default=None, alias='connectionUsageType') + connectionorganization: Optional[str] = Field(default=None, alias='connectionOrganization') diff --git a/appwrite/models/log.py b/appwrite/models/log.py index dc0e0c67..6824028e 100644 --- a/appwrite/models/log.py +++ b/appwrite/models/log.py @@ -20,7 +20,7 @@ class Log(AppwriteModel): mode : str API mode when event triggered. usertype : str - User type who triggered the audit log. Possible values: user, admin, guest, keyProject, keyAccount, keyOrganization. + User type who triggered the audit log. Possible values: user, admin, guest, hidden, keyProject, keyAccount, keyOrganization. ip : str IP session in use when the session was created. time : str diff --git a/appwrite/models/o_auth2_appwrite.py b/appwrite/models/o_auth2_appwrite.py new file mode 100644 index 00000000..002a8408 --- /dev/null +++ b/appwrite/models/o_auth2_appwrite.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class OAuth2Appwrite(AppwriteModel): + """ + OAuth2Appwrite + + Attributes + ---------- + id : str + OAuth2 provider ID. + enabled : bool + OAuth2 provider is active and can be used to create sessions. + clientid : str + Appwrite OAuth2 client ID. + clientsecret : str + Appwrite OAuth2 client secret. + """ + id: str = Field(..., alias='$id') + enabled: bool = Field(..., alias='enabled') + clientid: str = Field(..., alias='clientId') + clientsecret: str = Field(..., alias='clientSecret') diff --git a/appwrite/models/o_auth2_oidc.py b/appwrite/models/o_auth2_oidc.py index 6b896196..0ad06fef 100644 --- a/appwrite/models/o_auth2_oidc.py +++ b/appwrite/models/o_auth2_oidc.py @@ -2,6 +2,7 @@ from pydantic import Field, PrivateAttr from .base_model import AppwriteModel +from ..enums.o_auth2_oidc_prompt import OAuth2OidcPrompt class OAuth2Oidc(AppwriteModel): """ @@ -25,6 +26,10 @@ class OAuth2Oidc(AppwriteModel): OpenID Connect token endpoint URL. userinfourl : str OpenID Connect user info endpoint URL. + prompt : List[OAuth2OidcPrompt] + OpenID Connect prompt values controlling the authentication and consent screens. + maxage : Optional[float] + Maximum authentication age in seconds. When set, the user must have authenticated within this many seconds. """ id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') @@ -34,3 +39,5 @@ class OAuth2Oidc(AppwriteModel): authorizationurl: str = Field(..., alias='authorizationURL') tokenurl: str = Field(..., alias='tokenURL') userinfourl: str = Field(..., alias='userInfoURL') + prompt: List[OAuth2OidcPrompt] = Field(..., alias='prompt') + maxage: Optional[float] = Field(default=None, alias='maxAge') diff --git a/appwrite/models/o_auth2_provider_list.py b/appwrite/models/o_auth2_provider_list.py index b07ce754..e13f865a 100644 --- a/appwrite/models/o_auth2_provider_list.py +++ b/appwrite/models/o_auth2_provider_list.py @@ -33,6 +33,7 @@ from .o_auth2_tradeshift import OAuth2Tradeshift from .o_auth2_paypal import OAuth2Paypal from .o_auth2_gitlab import OAuth2Gitlab +from .o_auth2_appwrite import OAuth2Appwrite from .o_auth2_authentik import OAuth2Authentik from .o_auth2_auth0 import OAuth2Auth0 from .o_auth2_fusion_auth import OAuth2FusionAuth @@ -51,8 +52,8 @@ class OAuth2ProviderList(AppwriteModel): ---------- total : float Total number of OAuth2 providers in the given project. - providers : List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] + providers : List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Appwrite, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] List of OAuth2 providers. """ total: float = Field(..., alias='total') - providers: List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] = Field(..., alias='providers') + providers: List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Appwrite, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] = Field(..., alias='providers') diff --git a/appwrite/models/oauth2_grant.py b/appwrite/models/oauth2_grant.py index a17a74fd..58676082 100644 --- a/appwrite/models/oauth2_grant.py +++ b/appwrite/models/oauth2_grant.py @@ -21,6 +21,8 @@ class Oauth2Grant(AppwriteModel): ID of the OAuth2 client (app) the grant was requested for. scopes : List[Any] Requested OAuth2 scopes the user is being asked to consent to. + resources : List[Any] + Requested RFC 8707 resource indicators the user is being asked to consent to. authorizationdetails : str Requested authorization_details the user is being asked to consent to, as a JSON string. Each entry has a `type` plus project-defined fields. prompt : str @@ -38,6 +40,7 @@ class Oauth2Grant(AppwriteModel): userid: str = Field(..., alias='userId') appid: str = Field(..., alias='appId') scopes: List[Any] = Field(..., alias='scopes') + resources: List[Any] = Field(..., alias='resources') authorizationdetails: str = Field(..., alias='authorizationDetails') prompt: str = Field(..., alias='prompt') redirecturi: str = Field(..., alias='redirectUri') diff --git a/appwrite/models/health_queue.py b/appwrite/models/oauth2_organization.py similarity index 55% rename from appwrite/models/health_queue.py rename to appwrite/models/oauth2_organization.py index f9dcf66f..4481c4b2 100644 --- a/appwrite/models/health_queue.py +++ b/appwrite/models/oauth2_organization.py @@ -3,13 +3,13 @@ from .base_model import AppwriteModel -class HealthQueue(AppwriteModel): +class Oauth2Organization(AppwriteModel): """ - Health Queue + OAuth2 Organization Attributes ---------- - size : float - Amount of actions in the queue. + id : str + Organization ID. """ - size: float = Field(..., alias='size') + id: str = Field(..., alias='$id') diff --git a/appwrite/models/oauth2_organization_list.py b/appwrite/models/oauth2_organization_list.py new file mode 100644 index 00000000..aee823a0 --- /dev/null +++ b/appwrite/models/oauth2_organization_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .oauth2_organization import Oauth2Organization + +class Oauth2OrganizationList(AppwriteModel): + """ + OAuth2 accessible organizations list + + Attributes + ---------- + total : float + Total number of organizations that matched your query. + organizations : List[Oauth2Organization] + List of organizations. + """ + total: float = Field(..., alias='total') + organizations: List[Oauth2Organization] = Field(..., alias='organizations') diff --git a/appwrite/models/oauth2_par.py b/appwrite/models/oauth2_par.py new file mode 100644 index 00000000..a5942c86 --- /dev/null +++ b/appwrite/models/oauth2_par.py @@ -0,0 +1,18 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Oauth2PAR(AppwriteModel): + """ + OAuth2 PAR + + Attributes + ---------- + request_uri : str + Authorization request handle to pass to the authorize endpoint. + expires_in : float + Lifetime of the authorization request handle in seconds. + """ + request_uri: str = Field(..., alias='request_uri') + expires_in: float = Field(..., alias='expires_in') diff --git a/appwrite/models/oauth2_project.py b/appwrite/models/oauth2_project.py new file mode 100644 index 00000000..f7bac058 --- /dev/null +++ b/appwrite/models/oauth2_project.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Oauth2Project(AppwriteModel): + """ + OAuth2 Project + + Attributes + ---------- + id : str + Project ID. + region : str + Region ID the project is deployed in. + endpoint : str + API endpoint of the region the project is deployed in. Empty when the region has no public hostname configured. + """ + id: str = Field(..., alias='$id') + region: str = Field(..., alias='region') + endpoint: str = Field(..., alias='endpoint') diff --git a/appwrite/models/oauth2_project_list.py b/appwrite/models/oauth2_project_list.py new file mode 100644 index 00000000..e67b8929 --- /dev/null +++ b/appwrite/models/oauth2_project_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .oauth2_project import Oauth2Project + +class Oauth2ProjectList(AppwriteModel): + """ + OAuth2 accessible projects list + + Attributes + ---------- + total : float + Total number of projects that matched your query. + projects : List[Oauth2Project] + List of projects. + """ + total: float = Field(..., alias='total') + projects: List[Oauth2Project] = Field(..., alias='projects') diff --git a/appwrite/models/organization.py b/appwrite/models/organization.py new file mode 100644 index 00000000..95f4bdef --- /dev/null +++ b/appwrite/models/organization.py @@ -0,0 +1,132 @@ +from typing import Any, Dict, List, Optional, Union, cast, Generic, TypeVar, Type +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .preferences import Preferences +from .billing_plan import BillingPlan +from .billing_limits import BillingLimits + +T = TypeVar('T') + +class Organization(AppwriteModel, Generic[T]): + """ + Organization + + Attributes + ---------- + id : str + Team ID. + createdat : str + Team creation date in ISO 8601 format. + updatedat : str + Team update date in ISO 8601 format. + name : str + Team name. + total : float + Total number of team members. + prefs : Preferences[T] + Team preferences as a key-value object + billingbudget : float + Project budget limit + budgetalerts : List[Any] + Project budget limit + billingplan : str + Organization's billing plan ID. + billingplanid : str + Organization's billing plan ID. + billingplandetails : BillingPlan + Organization's billing plan. + billingemail : str + Billing email set for the organization. + billingstartdate : str + Billing cycle start date. + billingcurrentinvoicedate : str + Current invoice cycle start date. + billingnextinvoicedate : str + Next invoice cycle start date. + billingtrialstartdate : str + Start date of trial. + billingtrialdays : float + Number of trial days. + billingaggregationid : str + Current active aggregation id. + billinginvoiceid : str + Current active aggregation id. + paymentmethodid : str + Default payment method. + billingaddressid : str + Default payment method. + backuppaymentmethodid : str + Backup payment method. + status : str + Team status. + remarks : str + Remarks on team status. + agreementbaa : str + Organization agreements + programmanagername : str + Program manager's name. + programmanagercalendar : str + Program manager's calendar link. + programdiscordchannelname : str + Program's discord channel name. + programdiscordchannelurl : str + Program's discord channel URL. + billinglimits : Optional[BillingLimits] + Billing limits reached + billingplandowngrade : str + Billing plan selected for downgrade. + billingtaxid : str + Tax Id + markedfordeletion : bool + Marked for deletion + platform : str + Product with which the organization is associated (appwrite or imagine) + projects : List[Any] + Selected projects + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + name: str = Field(..., alias='name') + total: float = Field(..., alias='total') + prefs: Preferences[T] = Field(..., alias='prefs') + billingbudget: float = Field(..., alias='billingBudget') + budgetalerts: List[Any] = Field(..., alias='budgetAlerts') + billingplan: str = Field(..., alias='billingPlan') + billingplanid: str = Field(..., alias='billingPlanId') + billingplandetails: BillingPlan = Field(..., alias='billingPlanDetails') + billingemail: str = Field(..., alias='billingEmail') + billingstartdate: str = Field(..., alias='billingStartDate') + billingcurrentinvoicedate: str = Field(..., alias='billingCurrentInvoiceDate') + billingnextinvoicedate: str = Field(..., alias='billingNextInvoiceDate') + billingtrialstartdate: str = Field(..., alias='billingTrialStartDate') + billingtrialdays: float = Field(..., alias='billingTrialDays') + billingaggregationid: str = Field(..., alias='billingAggregationId') + billinginvoiceid: str = Field(..., alias='billingInvoiceId') + paymentmethodid: str = Field(..., alias='paymentMethodId') + billingaddressid: str = Field(..., alias='billingAddressId') + backuppaymentmethodid: str = Field(..., alias='backupPaymentMethodId') + status: str = Field(..., alias='status') + remarks: str = Field(..., alias='remarks') + agreementbaa: str = Field(..., alias='agreementBAA') + programmanagername: str = Field(..., alias='programManagerName') + programmanagercalendar: str = Field(..., alias='programManagerCalendar') + programdiscordchannelname: str = Field(..., alias='programDiscordChannelName') + programdiscordchannelurl: str = Field(..., alias='programDiscordChannelUrl') + billinglimits: Optional[BillingLimits] = Field(default=None, alias='billingLimits') + billingplandowngrade: str = Field(..., alias='billingPlanDowngrade') + billingtaxid: str = Field(..., alias='billingTaxId') + markedfordeletion: bool = Field(..., alias='markedForDeletion') + platform: str = Field(..., alias='platform') + projects: List[Any] = Field(..., alias='projects') + + @classmethod + def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Organization[T]': + """Create Organization instance with typed data.""" + instance = cls.model_validate(data) + if 'prefs' in data and data['prefs'] is not None: + instance.prefs = Preferences.with_data( + data['prefs'], model_type + ) + return instance diff --git a/appwrite/models/preferences.py b/appwrite/models/preferences.py index ce469590..73a68a21 100644 --- a/appwrite/models/preferences.py +++ b/appwrite/models/preferences.py @@ -29,6 +29,17 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) + def model_dump(self, **kwargs) -> Dict[str, Any]: + result = super().model_dump(**kwargs) + if hasattr(self, '_data'): + if isinstance(self._data, dict): + result['data'] = self._data + elif hasattr(self._data, 'model_dump'): + result['data'] = self._data.model_dump(**kwargs) + else: + result['data'] = self._data + return result + def to_dict(self) -> Dict[str, Any]: result = super().to_dict() if hasattr(self, '_data'): diff --git a/appwrite/models/program.py b/appwrite/models/program.py new file mode 100644 index 00000000..49f068e9 --- /dev/null +++ b/appwrite/models/program.py @@ -0,0 +1,39 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Program(AppwriteModel): + """ + Program + + Attributes + ---------- + id : str + Program ID + title : str + Program title + description : str + Program description + tag : str + Program tag for highlighting on console + icon : str + Program icon for highlighting on console + url : str + URL for more information on this program + active : bool + Whether this program is active + external : bool + Whether this program is external + billingplanid : str + Billing plan ID that this is program is associated with. + """ + id: str = Field(..., alias='$id') + title: str = Field(..., alias='title') + description: str = Field(..., alias='description') + tag: str = Field(..., alias='tag') + icon: str = Field(..., alias='icon') + url: str = Field(..., alias='url') + active: bool = Field(..., alias='active') + external: bool = Field(..., alias='external') + billingplanid: str = Field(..., alias='billingPlanId') diff --git a/appwrite/models/project.py b/appwrite/models/project.py index afd4b5a5..38e41404 100644 --- a/appwrite/models/project.py +++ b/appwrite/models/project.py @@ -57,6 +57,8 @@ class Project(AppwriteModel): Labels for the project. status : str Project status + onboarding : Dict[str, Any] + Stage progress (completed or skipped) with timestamps and actor types, keyed by stage id. authmethods : List[ProjectAuthMethod] List of auth methods. services : List[ProjectService] @@ -75,6 +77,8 @@ class Project(AppwriteModel): OAuth2 server authorization URL oauth2serverscopes : Optional[List[Any]] OAuth2 server allowed scopes + oauth2serverdefaultscopes : Optional[List[Any]] + OAuth2 server scopes used when an authorization request omits the scope parameter oauth2serverauthorizationdetailstypes : Optional[List[Any]] OAuth2 server accepted RFC 9396 authorization_details types oauth2serveraccesstokenduration : Optional[float] @@ -119,6 +123,7 @@ class Project(AppwriteModel): pingedat: str = Field(..., alias='pingedAt') labels: List[Any] = Field(..., alias='labels') status: str = Field(..., alias='status') + onboarding: Dict[str, Any] = Field(..., alias='onboarding') authmethods: List[ProjectAuthMethod] = Field(..., alias='authMethods') services: List[ProjectService] = Field(..., alias='services') protocols: List[ProjectProtocol] = Field(..., alias='protocols') @@ -128,6 +133,7 @@ class Project(AppwriteModel): oauth2serverenabled: Optional[bool] = Field(default=None, alias='oAuth2ServerEnabled') oauth2serverauthorizationurl: Optional[str] = Field(default=None, alias='oAuth2ServerAuthorizationUrl') oauth2serverscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerScopes') + oauth2serverdefaultscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerDefaultScopes') oauth2serverauthorizationdetailstypes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerAuthorizationDetailsTypes') oauth2serveraccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerAccessTokenDuration') oauth2serverrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerRefreshTokenDuration') diff --git a/appwrite/models/row.py b/appwrite/models/row.py index 8ccc97e4..e6e15976 100644 --- a/appwrite/models/row.py +++ b/appwrite/models/row.py @@ -57,6 +57,17 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) + def model_dump(self, **kwargs) -> Dict[str, Any]: + result = super().model_dump(**kwargs) + if hasattr(self, '_data'): + if isinstance(self._data, dict): + result['data'] = self._data + elif hasattr(self._data, 'model_dump'): + result['data'] = self._data.model_dump(**kwargs) + else: + result['data'] = self._data + return result + def to_dict(self) -> Dict[str, Any]: result = super().to_dict() if hasattr(self, '_data'): diff --git a/appwrite/models/usage_billing_plan.py b/appwrite/models/usage_billing_plan.py new file mode 100644 index 00000000..a078e726 --- /dev/null +++ b/appwrite/models/usage_billing_plan.py @@ -0,0 +1,46 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .additional_resource import AdditionalResource + +class UsageBillingPlan(AppwriteModel): + """ + usageBillingPlan + + Attributes + ---------- + bandwidth : AdditionalResource + Bandwidth additional resources + executions : AdditionalResource + Executions additional resources + member : AdditionalResource + Member additional resources + realtime : AdditionalResource + Realtime additional resources + realtimemessages : AdditionalResource + Realtime messages additional resources + realtimebandwidth : AdditionalResource + Realtime bandwidth additional resources + storage : AdditionalResource + Storage additional resources + users : AdditionalResource + User additional resources + gbhours : AdditionalResource + GBHour additional resources + imagetransformations : AdditionalResource + Image transformation additional resources + credits : AdditionalResource + Credits additional resources + """ + bandwidth: AdditionalResource = Field(..., alias='bandwidth') + executions: AdditionalResource = Field(..., alias='executions') + member: AdditionalResource = Field(..., alias='member') + realtime: AdditionalResource = Field(..., alias='realtime') + realtimemessages: AdditionalResource = Field(..., alias='realtimeMessages') + realtimebandwidth: AdditionalResource = Field(..., alias='realtimeBandwidth') + storage: AdditionalResource = Field(..., alias='storage') + users: AdditionalResource = Field(..., alias='users') + gbhours: AdditionalResource = Field(..., alias='GBHours') + imagetransformations: AdditionalResource = Field(..., alias='imageTransformations') + credits: AdditionalResource = Field(..., alias='credits') diff --git a/appwrite/models/usage_data_point.py b/appwrite/models/usage_data_point.py deleted file mode 100644 index a314956c..00000000 --- a/appwrite/models/usage_data_point.py +++ /dev/null @@ -1,60 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel - -class UsageDataPoint(AppwriteModel): - """ - usageDataPoint - - Attributes - ---------- - time : str - Bucket start timestamp (ISO 8601). When `interval` is omitted this is the request end time, marking the aggregate as-of moment. - value : float - Aggregated value for the bucket. - path : Optional[str] - API endpoint path when broken down by `path`. - method : Optional[str] - HTTP method when broken down by `method`. - status : Optional[str] - HTTP status code when broken down by `status`. - service : Optional[str] - API service segment when broken down by `service`. - country : Optional[str] - Country code when broken down by `country`. - region : Optional[str] - Appwrite region when broken down by `region`. - hostname : Optional[str] - Caller origin hostname when broken down by `hostname`. - osname : Optional[str] - Operating system name when broken down by `osName`. - clienttype : Optional[str] - Client type when broken down by `clientType`. - clientname : Optional[str] - Client name when broken down by `clientName`. - devicename : Optional[str] - Device classification when broken down by `deviceName`. - teamid : Optional[str] - Owning team ID when broken down by `teamId`. - resourceid : Optional[str] - External resource ID when broken down by `resourceId`. - resource : Optional[str] - Resource type when broken down by `resource` (gauges only). - """ - time: str = Field(..., alias='time') - value: float = Field(..., alias='value') - path: Optional[str] = Field(default=None, alias='path') - method: Optional[str] = Field(default=None, alias='method') - status: Optional[str] = Field(default=None, alias='status') - service: Optional[str] = Field(default=None, alias='service') - country: Optional[str] = Field(default=None, alias='country') - region: Optional[str] = Field(default=None, alias='region') - hostname: Optional[str] = Field(default=None, alias='hostname') - osname: Optional[str] = Field(default=None, alias='osName') - clienttype: Optional[str] = Field(default=None, alias='clientType') - clientname: Optional[str] = Field(default=None, alias='clientName') - devicename: Optional[str] = Field(default=None, alias='deviceName') - teamid: Optional[str] = Field(default=None, alias='teamId') - resourceid: Optional[str] = Field(default=None, alias='resourceId') - resource: Optional[str] = Field(default=None, alias='resource') diff --git a/appwrite/models/usage_event_list.py b/appwrite/models/usage_event_list.py deleted file mode 100644 index c183c3e4..00000000 --- a/appwrite/models/usage_event_list.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from .usage_metric import UsageMetric - -class UsageEventList(AppwriteModel): - """ - usageEventList - - Attributes - ---------- - interval : str - Time interval size (1h or 1d). Empty when the request omits `interval` — points then carry the request end time as their as-of marker. - metrics : List[UsageMetric] - One entry per requested metric, each carrying its own points[] time series (sums per bucket / dimension over time). - """ - interval: str = Field(..., alias='interval') - metrics: List[UsageMetric] = Field(..., alias='metrics') diff --git a/appwrite/models/usage_gauge_list.py b/appwrite/models/usage_gauge_list.py deleted file mode 100644 index ee3727ae..00000000 --- a/appwrite/models/usage_gauge_list.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from .usage_metric import UsageMetric - -class UsageGaugeList(AppwriteModel): - """ - usageGaugeList - - Attributes - ---------- - interval : str - Time interval size (1h or 1d). Empty when the request omits `interval` — points then carry the request end time as their as-of marker. - metrics : List[UsageMetric] - One entry per requested metric, each carrying its own points[] time series (latest-snapshot per bucket / dimension via argMax over time). - """ - interval: str = Field(..., alias='interval') - metrics: List[UsageMetric] = Field(..., alias='metrics') diff --git a/appwrite/models/usage_metric.py b/appwrite/models/usage_metric.py deleted file mode 100644 index 3cd15d47..00000000 --- a/appwrite/models/usage_metric.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from .usage_data_point import UsageDataPoint - -class UsageMetric(AppwriteModel): - """ - usageMetric - - Attributes - ---------- - metric : str - Metric key this series describes. - points : List[UsageDataPoint] - Data points for this metric, ordered by time ascending. With `interval`, each entry is one bucket; without, each entry is one row of the dimensional or aggregate breakdown. - """ - metric: str = Field(..., alias='metric') - points: List[UsageDataPoint] = Field(..., alias='points') diff --git a/appwrite/query.py b/appwrite/query.py index c223a4e1..3dafd4aa 100644 --- a/appwrite/query.py +++ b/appwrite/query.py @@ -248,6 +248,18 @@ def distance_greater_than(attribute, values, distance, meters=True): def distance_less_than(attribute, values, distance, meters=True): return str(Query("distanceLessThan", attribute, [[values, distance, meters]])) + @staticmethod + def vector_dot(attribute, vector): + return str(Query("vectorDot", attribute, [vector])) + + @staticmethod + def vector_cosine(attribute, vector): + return str(Query("vectorCosine", attribute, [vector])) + + @staticmethod + def vector_euclidean(attribute, vector): + return str(Query("vectorEuclidean", attribute, [vector])) + @staticmethod def intersects(attribute, values): return str(Query("intersects", attribute, [values])) diff --git a/appwrite/services/account.py b/appwrite/services/account.py index 21b734d1..5af533a9 100644 --- a/appwrite/services/account.py +++ b/appwrite/services/account.py @@ -1606,7 +1606,7 @@ def create_o_auth2_token( Parameters ---------- provider : OAuthProvider - OAuth2 Provider. Currently, supported providers are: amazon, apple, auth0, authentik, autodesk, bitbucket, bitly, box, dailymotion, discord, disqus, dropbox, etsy, facebook, figma, fusionauth, github, gitlab, google, keycloak, kick, linkedin, microsoft, notion, oidc, okta, paypal, paypalSandbox, podio, salesforce, slack, spotify, stripe, tradeshift, tradeshiftBox, twitch, wordpress, x, yahoo, yammer, yandex, zoho, zoom. + OAuth2 Provider. Currently, supported providers are: amazon, apple, appwrite, auth0, authentik, autodesk, bitbucket, bitly, box, dailymotion, discord, disqus, dropbox, etsy, facebook, figma, fusionauth, github, gitlab, google, keycloak, kick, linkedin, microsoft, notion, oidc, okta, paypal, paypalSandbox, podio, salesforce, slack, spotify, stripe, tradeshift, tradeshiftBox, twitch, wordpress, x, yahoo, yammer, yandex, zoho, zoom. success : Optional[str] URL to redirect back to your app after a successful login attempt. Only URLs from hostnames in your project's platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. failure : Optional[str] diff --git a/appwrite/services/apps.py b/appwrite/services/apps.py index da3c25d3..ab3e9110 100644 --- a/appwrite/services/apps.py +++ b/appwrite/services/apps.py @@ -396,6 +396,53 @@ def delete( return response + def update_labels( + self, + app_id: str, + labels: List[str] + ) -> App: + """ + Update the labels of an application. Labels are read-only for clients; only a server SDK using a project API key can set them. Replaces the previous labels. + + Parameters + ---------- + app_id : str + Application unique ID. + labels : List[str] + Array of application labels. Replaces the previous labels. Maximum of 1000 labels are allowed, each up to 36 alphanumeric characters long. + + Returns + ------- + App + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/labels' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if labels is None: + raise AppwriteException('Missing required parameter: "labels"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + + api_params['labels'] = self._normalize_value(labels) + + response = self.client.call('put', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=App) + + def list_secrets( self, app_id: str, diff --git a/appwrite/services/backups.py b/appwrite/services/backups.py index a13743d6..fda14881 100644 --- a/appwrite/services/backups.py +++ b/appwrite/services/backups.py @@ -429,10 +429,14 @@ def create_restoration( archive_id: str, services: List[BackupServices], new_resource_id: Optional[str] = None, - new_resource_name: Optional[str] = None + new_resource_name: Optional[str] = None, + new_specification: Optional[str] = None ) -> BackupRestoration: """ Create and trigger a new restoration for a backup on a project. + + When restoring a DocumentsDB or VectorsDB database to a new resource, pass `newSpecification` to provision the restored database on a different specification than the archived one (for example, restoring onto a larger or smaller dedicated database). Use `serverless` to restore onto the shared pool, or a dedicated specification slug to restore onto a dedicated database of that size. The specification must be permitted by the organization's plan. `newSpecification` is not supported for legacy/TablesDB databases or for bucket restores. + Parameters ---------- @@ -444,6 +448,8 @@ def create_restoration( Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. new_resource_name : Optional[str] Database name. Max length: 128 chars. + new_specification : Optional[str] + Specification to provision the restored database on, when restoring a DocumentsDB or VectorsDB database to a new resource. Defaults to the archived database's specification. Use `serverless` for the shared pool or a dedicated specification slug. Returns ------- @@ -471,6 +477,8 @@ def create_restoration( api_params['newResourceId'] = self._normalize_value(new_resource_id) if new_resource_name is not None: api_params['newResourceName'] = self._normalize_value(new_resource_name) + if new_specification is not None: + api_params['newSpecification'] = self._normalize_value(new_specification) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/functions.py b/appwrite/services/functions.py index 7d9a0f14..18709fb2 100644 --- a/appwrite/services/functions.py +++ b/appwrite/services/functions.py @@ -126,7 +126,7 @@ def create( commands : Optional[str] Build Commands. scopes : Optional[List[ProjectKeyScopes]] - List of scopes allowed for API key auto-generated for every execution. Maximum of 100 scopes are allowed. + List of scopes allowed for API key auto-generated for every execution. Maximum of 200 scopes are allowed. installation_id : Optional[str] Appwrite Installation ID for VCS (Version Control System) deployment. provider_repository_id : Optional[str] @@ -251,11 +251,17 @@ def list_runtimes( def list_specifications( - self + self, + type: Optional[str] = None ) -> SpecificationList: """ List allowed function specifications for this instance. + Parameters + ---------- + type : Optional[str] + Specification type to list. Can be one of: runtimes, builds. + Returns ------- SpecificationList @@ -270,6 +276,9 @@ def list_specifications( api_path = '/functions/specifications' api_params = {} + if type is not None: + api_params['type'] = self._normalize_value(type) + response = self.client.call('get', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), 'accept': 'application/json', @@ -370,7 +379,7 @@ def update( commands : Optional[str] Build Commands. scopes : Optional[List[ProjectKeyScopes]] - List of scopes allowed for API Key auto-generated for every execution. Maximum of 100 scopes are allowed. + List of scopes allowed for API Key auto-generated for every execution. Maximum of 200 scopes are allowed. installation_id : Optional[str] Appwrite Installation ID for VCS (Version Controle System) deployment. provider_repository_id : Optional[str] @@ -445,8 +454,7 @@ def update( api_params['providerRootDirectory'] = self._normalize_value(provider_root_directory) api_params['providerBranches'] = self._normalize_value(provider_branches) api_params['providerPaths'] = self._normalize_value(provider_paths) - if build_specification is not None: - api_params['buildSpecification'] = self._normalize_value(build_specification) + api_params['buildSpecification'] = self._normalize_value(build_specification) if runtime_specification is not None: api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: @@ -968,7 +976,8 @@ def get_deployment_download( self, function_id: str, deployment_id: str, - type: Optional[DeploymentDownloadType] = None + type: Optional[DeploymentDownloadType] = None, + token: Optional[str] = None ) -> bytes: """ Get a function deployment content by its unique ID. The endpoint response return with a 'Content-Disposition: attachment' header that tells the browser to start downloading the file to user downloads directory. @@ -981,6 +990,8 @@ def get_deployment_download( Deployment ID. type : Optional[DeploymentDownloadType] Deployment file to download. Can be: "source", "output". + token : Optional[str] + Presigned source-download token for accessing this deployment without a session (jobs-service). Returns ------- @@ -1006,6 +1017,8 @@ def get_deployment_download( if type is not None: api_params['type'] = self._normalize_value(type) + if token is not None: + api_params['token'] = self._normalize_value(token) response = self.client.call('get', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/health.py b/appwrite/services/health.py deleted file mode 100644 index bbf93903..00000000 --- a/appwrite/services/health.py +++ /dev/null @@ -1,882 +0,0 @@ -from ..service import Service -from urllib.parse import quote -from typing import Any, Dict, List, Optional, Union -from ..exception import AppwriteException -from appwrite.utils.deprecated import deprecated -from ..models.health_status import HealthStatus -from ..models.health_antivirus import HealthAntivirus -from ..models.health_status_list import HealthStatusList -from ..models.health_certificate import HealthCertificate -from ..models.health_queue import HealthQueue -from ..enums.health_queue_name import HealthQueueName -from ..models.health_time import HealthTime - -class Health(Service): - - def __init__(self, client) -> None: - super(Health, self).__init__(client) - - def get( - self - ) -> HealthStatus: - """ - Check the Appwrite HTTP server is up and responsive. - - Returns - ------- - HealthStatus - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatus) - - - def get_antivirus( - self - ) -> HealthAntivirus: - """ - Check the Appwrite Antivirus server is up and connection is successful. - - Returns - ------- - HealthAntivirus - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/anti-virus' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthAntivirus) - - - def get_audits_db( - self - ) -> HealthStatusList: - """ - Check the database that backs the audit and activity store. When the connection is reachable the endpoint returns a passing status with its response time. - - - Returns - ------- - HealthStatusList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/audits-db' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatusList) - - - def get_cache( - self - ) -> HealthStatusList: - """ - Check the Appwrite in-memory cache servers are up and connection is successful. - - Returns - ------- - HealthStatusList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/cache' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatusList) - - - def get_certificate( - self, - domain: Optional[str] = None - ) -> HealthCertificate: - """ - Get the SSL certificate for a domain - - Parameters - ---------- - domain : Optional[str] - string - - Returns - ------- - HealthCertificate - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/certificate' - api_params = {} - - if domain is not None: - api_params['domain'] = self._normalize_value(domain) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthCertificate) - - - def get_console_pausing( - self, - threshold: Optional[float] = None, - inactivity_days: Optional[float] = None - ) -> HealthStatus: - """ - Get console pausing health status. Monitors projects approaching the pause threshold to detect potential issues with console access tracking. - - - Parameters - ---------- - threshold : Optional[float] - Percentage threshold of projects approaching pause. When hit (equal or higher), endpoint returns server error. Default value is 10. - inactivity_days : Optional[float] - Number of days of inactivity before a project is paused. Should match the plan's projectInactivityDays setting. Default value is 7. - - Returns - ------- - HealthStatus - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/console-pausing' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - if inactivity_days is not None: - api_params['inactivityDays'] = self._normalize_value(inactivity_days) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatus) - - - def get_db( - self - ) -> HealthStatusList: - """ - Check the Appwrite database servers are up and connection is successful. - - Returns - ------- - HealthStatusList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/db' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatusList) - - - def get_pub_sub( - self - ) -> HealthStatusList: - """ - Check the Appwrite pub-sub servers are up and connection is successful. - - Returns - ------- - HealthStatusList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/pubsub' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatusList) - - - def get_queue_audits( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of audit logs that are waiting to be processed in the Appwrite internal queue server. - - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/audits' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_builds( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of builds that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/builds' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_certificates( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of certificates that are waiting to be issued against [Letsencrypt](https://letsencrypt.org/) in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/certificates' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_databases( - self, - name: Optional[str] = None, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of database changes that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - name : Optional[str] - Queue name for which to check the queue size - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/databases' - api_params = {} - - if name is not None: - api_params['name'] = self._normalize_value(name) - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_deletes( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of background destructive changes that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/deletes' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_failed_jobs( - self, - name: HealthQueueName, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Returns the amount of failed jobs in a given queue. - - - Parameters - ---------- - name : HealthQueueName - The name of the queue - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/failed/{name}' - api_params = {} - if name is None: - raise AppwriteException('Missing required parameter: "name"') - - api_path = api_path.replace('{name}', str(self._normalize_value(name))) - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_functions( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of function executions that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/functions' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_logs( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of logs that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/logs' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_mails( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of mails that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/mails' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_messaging( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of messages that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/messaging' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_migrations( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of migrations that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/migrations' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_stats_resources( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of metrics that are waiting to be processed in the Appwrite stats resources queue. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/stats-resources' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_usage( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of metrics that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/stats-usage' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_queue_webhooks( - self, - threshold: Optional[float] = None - ) -> HealthQueue: - """ - Get the number of webhooks that are waiting to be processed in the Appwrite internal queue server. - - Parameters - ---------- - threshold : Optional[float] - Queue size threshold. When hit (equal or higher), endpoint returns server error. Default value is 5000. - - Returns - ------- - HealthQueue - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/queue/webhooks' - api_params = {} - - if threshold is not None: - api_params['threshold'] = self._normalize_value(threshold) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthQueue) - - - def get_storage( - self - ) -> HealthStatus: - """ - Check the Appwrite storage device is up and connection is successful. - - Returns - ------- - HealthStatus - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/storage' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatus) - - - def get_storage_local( - self - ) -> HealthStatus: - """ - Check the Appwrite local storage device is up and connection is successful. - - Returns - ------- - HealthStatus - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/storage/local' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthStatus) - - - def get_time( - self - ) -> HealthTime: - """ - Check the Appwrite server time is synced with Google remote NTP server. We use this technology to smoothly handle leap seconds with no disruptive events. The [Network Time Protocol](https://en.wikipedia.org/wiki/Network_Time_Protocol) (NTP) is used by hundreds of millions of computers and devices to synchronize their clocks over the Internet. If your computer sets its own clock, it likely uses NTP. - - Returns - ------- - HealthTime - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/health/time' - api_params = {} - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=HealthTime) - diff --git a/appwrite/services/messaging.py b/appwrite/services/messaging.py index 065a9537..3abb1004 100644 --- a/appwrite/services/messaging.py +++ b/appwrite/services/messaging.py @@ -6,7 +6,6 @@ from ..models.message_list import MessageList from ..models.message import Message from ..enums.message_priority import MessagePriority -from ..models.log_list import LogList from ..models.target_list import TargetList from ..models.provider_list import ProviderList from ..models.provider import Provider @@ -707,55 +706,6 @@ def delete( return response - def list_message_logs( - self, - message_id: str, - queries: Optional[List[str]] = None, - total: Optional[bool] = None - ) -> LogList: - """ - Get the message activity logs listed by its unique ID. - - Parameters - ---------- - message_id : str - Message ID. - queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset - total : Optional[bool] - When set to false, the total count returned will be 0 and will not be calculated. - - Returns - ------- - LogList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/messaging/messages/{messageId}/logs' - api_params = {} - if message_id is None: - raise AppwriteException('Missing required parameter: "message_id"') - - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - - if queries is not None: - api_params['queries'] = self._normalize_value(queries) - if total is not None: - api_params['total'] = self._normalize_value(total) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=LogList) - - def list_targets( self, message_id: str, @@ -2686,104 +2636,6 @@ def delete_provider( return response - def list_provider_logs( - self, - provider_id: str, - queries: Optional[List[str]] = None, - total: Optional[bool] = None - ) -> LogList: - """ - Get the provider activity logs listed by its unique ID. - - Parameters - ---------- - provider_id : str - Provider ID. - queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset - total : Optional[bool] - When set to false, the total count returned will be 0 and will not be calculated. - - Returns - ------- - LogList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/messaging/providers/{providerId}/logs' - api_params = {} - if provider_id is None: - raise AppwriteException('Missing required parameter: "provider_id"') - - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - - if queries is not None: - api_params['queries'] = self._normalize_value(queries) - if total is not None: - api_params['total'] = self._normalize_value(total) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=LogList) - - - def list_subscriber_logs( - self, - subscriber_id: str, - queries: Optional[List[str]] = None, - total: Optional[bool] = None - ) -> LogList: - """ - Get the subscriber activity logs listed by its unique ID. - - Parameters - ---------- - subscriber_id : str - Subscriber ID. - queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset - total : Optional[bool] - When set to false, the total count returned will be 0 and will not be calculated. - - Returns - ------- - LogList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/messaging/subscribers/{subscriberId}/logs' - api_params = {} - if subscriber_id is None: - raise AppwriteException('Missing required parameter: "subscriber_id"') - - api_path = api_path.replace('{subscriberId}', str(self._normalize_value(subscriber_id))) - - if queries is not None: - api_params['queries'] = self._normalize_value(queries) - if total is not None: - api_params['total'] = self._normalize_value(total) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=LogList) - - def list_topics( self, queries: Optional[List[str]] = None, @@ -3011,55 +2863,6 @@ def delete_topic( return response - def list_topic_logs( - self, - topic_id: str, - queries: Optional[List[str]] = None, - total: Optional[bool] = None - ) -> LogList: - """ - Get the topic activity logs listed by its unique ID. - - Parameters - ---------- - topic_id : str - Topic ID. - queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset - total : Optional[bool] - When set to false, the total count returned will be 0 and will not be calculated. - - Returns - ------- - LogList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/messaging/topics/{topicId}/logs' - api_params = {} - if topic_id is None: - raise AppwriteException('Missing required parameter: "topic_id"') - - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - - if queries is not None: - api_params['queries'] = self._normalize_value(queries) - if total is not None: - api_params['total'] = self._normalize_value(total) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=LogList) - - def list_subscribers( self, topic_id: str, diff --git a/appwrite/services/oauth2.py b/appwrite/services/oauth2.py index 581d4e4e..272fbc73 100644 --- a/appwrite/services/oauth2.py +++ b/appwrite/services/oauth2.py @@ -7,6 +7,9 @@ from ..models.oauth2_authorize import Oauth2Authorize from ..models.oauth2_device_authorization import Oauth2DeviceAuthorization from ..models.oauth2_grant import Oauth2Grant +from ..models.oauth2_organization_list import Oauth2OrganizationList +from ..models.oauth2_par import Oauth2PAR +from ..models.oauth2_project_list import Oauth2ProjectList from ..models.oauth2_reject import Oauth2Reject from ..models.oauth2_token import Oauth2Token @@ -18,7 +21,8 @@ def __init__(self, client) -> None: def approve( self, grant_id: str, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, + scope: Optional[str] = None ) -> Oauth2Approve: """ Approve an OAuth2 grant after the user gives consent. Returns the `redirectUrl` the end user should be sent to. The consent screen may optionally pass enriched `authorization_details` to record the concrete resources the user selected. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. @@ -29,6 +33,8 @@ def approve( Grant ID made during authorization, provided to consent screen in URL search params. authorization_details : Optional[str] Enriched `authorization_details` the user consented to, replacing what the client requested. Each entry must use a `type` the project accepts. Optional; omit to keep the originally requested details. + scope : Optional[str] + Space-separated scopes the user consented to. Must be a subset of the scopes originally requested; identity scopes such as `openid` are always retained. Optional; omit to keep the originally requested scopes. Returns ------- @@ -51,6 +57,8 @@ def approve( api_params['grant_id'] = self._normalize_value(grant_id) if authorization_details is not None: api_params['authorization_details'] = self._normalize_value(authorization_details) + if scope is not None: + api_params['scope'] = self._normalize_value(scope) response = self.client.call('post', api_path, { 'content-type': 'application/json', @@ -62,31 +70,34 @@ def approve( def authorize( self, - client_id: str, - redirect_uri: str, - response_type: str, - scope: str, + client_id: Optional[str] = None, + redirect_uri: Optional[str] = None, + response_type: Optional[str] = None, + scope: Optional[str] = None, state: Optional[str] = None, nonce: Optional[str] = None, code_challenge: Optional[str] = None, code_challenge_method: Optional[str] = None, prompt: Optional[str] = None, max_age: Optional[float] = None, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, + resource: Optional[str] = None, + audience: Optional[str] = None, + request_uri: Optional[str] = None ) -> Oauth2Authorize: """ Begin the OAuth2 authorization flow. When called without a session, the user is redirected to the consent screen without grant ID. When called with a session, the redirect URL includes param for grant ID. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. Parameters ---------- - client_id : str + client_id : Optional[str] OAuth2 client ID. - redirect_uri : str + redirect_uri : Optional[str] Redirect URI where visitor will be redirected after authorization, whether successful or not. - response_type : str + response_type : Optional[str] OAuth2 / OIDC response type. One of `code` (Authorization Code Flow), `id_token` (Implicit Flow, OIDC login only), or `code id_token` (Hybrid Flow). - scope : str - Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`. + scope : Optional[str] + Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`, `phone`. state : Optional[str] OAuth2 state. You receive this back in the redirect URI. nonce : Optional[str] @@ -101,6 +112,12 @@ def authorize( OIDC max_age paraleter for customization of consent screen. Maximum allowable elapsed time in seconds since the user last authenticated. If exceeded, re-authentication is required. authorization_details : Optional[str] Rich authorization request. JSON array of objects, each with a `type` and project-defined fields + resource : Optional[str] + RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. + audience : Optional[str] + Compatibility alias for a single OAuth2 resource indicator URI. + request_uri : Optional[str] + OAuth2 authorization request handle returned by the pushed authorization request endpoint. Returns ------- @@ -115,24 +132,16 @@ def authorize( api_path = '/oauth2/{project_id}/authorize' api_params = {} - if client_id is None: - raise AppwriteException('Missing required parameter: "client_id"') - - if redirect_uri is None: - raise AppwriteException('Missing required parameter: "redirect_uri"') - - if response_type is None: - raise AppwriteException('Missing required parameter: "response_type"') - - if scope is None: - raise AppwriteException('Missing required parameter: "scope"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['client_id'] = self._normalize_value(client_id) - api_params['redirect_uri'] = self._normalize_value(redirect_uri) - api_params['response_type'] = self._normalize_value(response_type) - api_params['scope'] = self._normalize_value(scope) + if client_id is not None: + api_params['client_id'] = self._normalize_value(client_id) + if redirect_uri is not None: + api_params['redirect_uri'] = self._normalize_value(redirect_uri) + if response_type is not None: + api_params['response_type'] = self._normalize_value(response_type) + if scope is not None: + api_params['scope'] = self._normalize_value(scope) if state is not None: api_params['state'] = self._normalize_value(state) if nonce is not None: @@ -147,6 +156,12 @@ def authorize( api_params['max_age'] = self._normalize_value(max_age) if authorization_details is not None: api_params['authorization_details'] = self._normalize_value(authorization_details) + if resource is not None: + api_params['resource'] = self._normalize_value(resource) + if audience is not None: + api_params['audience'] = self._normalize_value(audience) + if request_uri is not None: + api_params['request_uri'] = self._normalize_value(request_uri) response = self.client.call('get', api_path, { 'accept': 'application/json', @@ -159,7 +174,9 @@ def create_device_authorization( self, client_id: Optional[str] = None, scope: Optional[str] = None, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, + resource: Optional[str] = None, + audience: Optional[str] = None ) -> Oauth2DeviceAuthorization: """ Start the OAuth2 Device Authorization Grant. Returns the device code, user code, verification URL, expiration, and polling interval. @@ -172,6 +189,10 @@ def create_device_authorization( Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`. authorization_details : Optional[str] Rich authorization request. JSON array of objects, each with a `type` and project-defined fields + resource : Optional[str] + RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. + audience : Optional[str] + Compatibility alias for a single OAuth2 resource indicator URI. Returns ------- @@ -194,6 +215,10 @@ def create_device_authorization( api_params['scope'] = self._normalize_value(scope) if authorization_details is not None: api_params['authorization_details'] = self._normalize_value(authorization_details) + if resource is not None: + api_params['resource'] = self._normalize_value(resource) + if audience is not None: + api_params['audience'] = self._normalize_value(audience) response = self.client.call('post', api_path, { 'content-type': 'application/json', @@ -282,6 +307,203 @@ def get_grant( return self._parse_response(response, model=Oauth2Grant) + def list_organizations( + self, + limit: Optional[float] = None, + offset: Optional[float] = None, + search: Optional[str] = None + ) -> Oauth2OrganizationList: + """ + List the organizations the OAuth2 access token can access. Resolves the token's `organization` authorization details, expanding the `*` wildcard into the concrete set of organizations the user can see. + + Parameters + ---------- + limit : Optional[float] + Maximum number of organizations to return. Between 1 and 5000. + offset : Optional[float] + Number of organizations to skip before returning results. Used for pagination. + search : Optional[str] + Search term to filter your list results. Max length: 256 chars. + + Returns + ------- + Oauth2OrganizationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/oauth2/{project_id}/organizations' + api_params = {} + api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) + + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + if search is not None: + api_params['search'] = self._normalize_value(search) + + response = self.client.call('get', api_path, { + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2OrganizationList) + + + def create_par( + self, + client_id: str, + redirect_uri: str, + response_type: str, + scope: Optional[str] = None, + state: Optional[str] = None, + nonce: Optional[str] = None, + code_challenge: Optional[str] = None, + code_challenge_method: Optional[str] = None, + prompt: Optional[str] = None, + max_age: Optional[float] = None, + authorization_details: Optional[str] = None, + resource: Optional[str] = None, + audience: Optional[str] = None + ) -> Oauth2PAR: + """ + Store an OAuth2 authorization request server-side and receive a short-lived request_uri handle for the authorize endpoint. + + Parameters + ---------- + client_id : str + OAuth2 client ID. + redirect_uri : str + Redirect URI where visitor will be redirected after authorization, whether successful or not. + response_type : str + OAuth2 / OIDC response type. + scope : Optional[str] + Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`, `phone`. + state : Optional[str] + OAuth2 state. You receive this back in the redirect URI. + nonce : Optional[str] + OIDC nonce parameter to prevent replay attacks. Required when response_type includes `id_token`. + code_challenge : Optional[str] + PKCE code challenge. Required when OAuth2 app is public. + code_challenge_method : Optional[str] + PKCE code challenge method. Required when OAuth2 app is public. + prompt : Optional[str] + OIDC prompt parameter for customization of consent screen. Space-separated list of: none, login, consent, select_account. + max_age : Optional[float] + OIDC max_age parameter for customization of consent screen. + authorization_details : Optional[str] + Rich authorization request. JSON array of objects, each with a `type` and project-defined fields + resource : Optional[str] + RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. + audience : Optional[str] + Compatibility alias for a single OAuth2 resource indicator URI. + + Returns + ------- + Oauth2PAR + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/oauth2/{project_id}/par' + api_params = {} + if client_id is None: + raise AppwriteException('Missing required parameter: "client_id"') + + if redirect_uri is None: + raise AppwriteException('Missing required parameter: "redirect_uri"') + + if response_type is None: + raise AppwriteException('Missing required parameter: "response_type"') + + api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) + + api_params['client_id'] = self._normalize_value(client_id) + api_params['redirect_uri'] = self._normalize_value(redirect_uri) + api_params['response_type'] = self._normalize_value(response_type) + if scope is not None: + api_params['scope'] = self._normalize_value(scope) + if state is not None: + api_params['state'] = self._normalize_value(state) + if nonce is not None: + api_params['nonce'] = self._normalize_value(nonce) + if code_challenge is not None: + api_params['code_challenge'] = self._normalize_value(code_challenge) + if code_challenge_method is not None: + api_params['code_challenge_method'] = self._normalize_value(code_challenge_method) + if prompt is not None: + api_params['prompt'] = self._normalize_value(prompt) + api_params['max_age'] = self._normalize_value(max_age) + if authorization_details is not None: + api_params['authorization_details'] = self._normalize_value(authorization_details) + if resource is not None: + api_params['resource'] = self._normalize_value(resource) + if audience is not None: + api_params['audience'] = self._normalize_value(audience) + + response = self.client.call('post', api_path, { + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2PAR) + + + def list_projects( + self, + limit: Optional[float] = None, + offset: Optional[float] = None, + search: Optional[str] = None + ) -> Oauth2ProjectList: + """ + List the projects the OAuth2 access token can access. Resolves the token's `project` authorization details, expanding the `*` wildcard into the concrete set of projects the user can see. + + Parameters + ---------- + limit : Optional[float] + Maximum number of projects to return. Between 1 and 5000. + offset : Optional[float] + Number of projects to skip before returning results. Used for pagination. + search : Optional[str] + Search term to filter your list results. Max length: 256 chars. + + Returns + ------- + Oauth2ProjectList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/oauth2/{project_id}/projects' + api_params = {} + api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) + + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + if search is not None: + api_params['search'] = self._normalize_value(search) + + response = self.client.call('get', api_path, { + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2ProjectList) + + def reject( self, grant_id: str @@ -386,7 +608,9 @@ def create_token( client_id: Optional[str] = None, client_secret: Optional[str] = None, code_verifier: Optional[str] = None, - redirect_uri: Optional[str] = None + redirect_uri: Optional[str] = None, + resource: Optional[str] = None, + audience: Optional[str] = None ) -> Oauth2Token: """ Exchange an OAuth2 authorization code, refresh token, or device code for access and refresh tokens. @@ -409,6 +633,10 @@ def create_token( PKCE code verifier. Required for public apps. redirect_uri : Optional[str] Redirect URI. Required for `authorization_code` grant type. + resource : Optional[str] + RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. + audience : Optional[str] + Compatibility alias for a single OAuth2 resource indicator URI. Returns ------- @@ -443,6 +671,10 @@ def create_token( api_params['code_verifier'] = self._normalize_value(code_verifier) if redirect_uri is not None: api_params['redirect_uri'] = self._normalize_value(redirect_uri) + if resource is not None: + api_params['resource'] = self._normalize_value(resource) + if audience is not None: + api_params['audience'] = self._normalize_value(audience) response = self.client.call('post', api_path, { 'content-type': 'application/json', diff --git a/appwrite/services/organization.py b/appwrite/services/organization.py index 7c63003a..eaf0ca88 100644 --- a/appwrite/services/organization.py +++ b/appwrite/services/organization.py @@ -1,20 +1,132 @@ from ..service import Service from urllib.parse import quote -from typing import Any, Dict, List, Optional, Union +from typing import Any, Dict, List, Optional, Union, Type, TypeVar from ..exception import AppwriteException from appwrite.utils.deprecated import deprecated +from ..models.organization import Organization as OrganizationModel from ..models.key_list import KeyList from ..enums.organization_key_scopes import OrganizationKeyScopes from ..models.key import Key +from ..models.membership_list import MembershipList +from ..models.membership import Membership from ..models.project_list import ProjectList from ..enums.region import Region from ..models.project import Project +T = TypeVar('T') + class Organization(Service): def __init__(self, client) -> None: super(Organization, self).__init__(client) + def get( + self, + model_type: Type[T] = dict + ) -> OrganizationModel[T]: + """ + Get the current organization. + + Parameters + ---------- + + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + OrganizationModel[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization' + api_params = {} + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return OrganizationModel.with_data(response, model_type) + + + def update( + self, + name: str, + model_type: Type[T] = dict + ) -> OrganizationModel[T]: + """ + Update the current organization's name. + + Parameters + ---------- + name : str + New organization name. Max length: 128 chars. + + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + OrganizationModel[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization' + api_params = {} + if name is None: + raise AppwriteException('Missing required parameter: "name"') + + + api_params['name'] = self._normalize_value(name) + + response = self.client.call('put', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return OrganizationModel.with_data(response, model_type) + + + def delete( + self + ) -> Dict[str, Any]: + """ + Delete the current organization. All projects that belong to the organization are deleted as well. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization' + api_params = {} + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, api_params) + + return response + + def list_keys( self, queries: Optional[List[str]] = None, @@ -74,7 +186,7 @@ def create_key( name : str Key name. Max length: 128 chars. scopes : List[OrganizationKeyScopes] - Key scopes list. Maximum of 100 scopes are allowed. + Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. @@ -171,7 +283,7 @@ def update_key( name : str Key name. Max length: 128 chars. scopes : List[OrganizationKeyScopes] - Key scopes list. Maximum of 100 scopes are allowed. + Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. @@ -251,6 +363,243 @@ def delete_key( return response + def list_memberships( + self, + queries: Optional[List[str]] = None, + search: Optional[str] = None, + total: Optional[bool] = None + ) -> MembershipList: + """ + Get a list of all memberships from the current organization. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: userId, teamId, invited, joined, confirm, roles + search : Optional[str] + Search term to filter your list results. Max length: 256 chars. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + MembershipList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/memberships' + api_params = {} + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if search is not None: + api_params['search'] = self._normalize_value(search) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=MembershipList) + + + def create_membership( + self, + roles: List[str], + email: Optional[str] = None, + user_id: Optional[str] = None, + phone: Optional[str] = None, + url: Optional[str] = None, + name: Optional[str] = None + ) -> Membership: + """ + Invite a new member to join the current organization. An email with a link to join the organization will be sent to the new member's email address. If member doesn't exist in the project it will be automatically created. + + Parameters + ---------- + roles : List[str] + Array of strings. Use this param to set the user roles in the organization. A role can be any string. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). Maximum of 100 roles are allowed, each 81 characters long. + email : Optional[str] + Email of the new organization member. + user_id : Optional[str] + ID of the user to be added to the organization. + phone : Optional[str] + Phone number. Format this number with a leading '+' and a country code, e.g., +16175551212. + url : Optional[str] + URL to redirect the user back to your app from the invitation email. This parameter is not required when an API key is supplied. + name : Optional[str] + Name of the new organization member. Max length: 128 chars. + + Returns + ------- + Membership + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/memberships' + api_params = {} + if roles is None: + raise AppwriteException('Missing required parameter: "roles"') + + + if email is not None: + api_params['email'] = self._normalize_value(email) + if user_id is not None: + api_params['userId'] = self._normalize_value(user_id) + if phone is not None: + api_params['phone'] = self._normalize_value(phone) + api_params['roles'] = self._normalize_value(roles) + if url is not None: + api_params['url'] = self._normalize_value(url) + if name is not None: + api_params['name'] = self._normalize_value(name) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Membership) + + + def get_membership( + self, + membership_id: str + ) -> Membership: + """ + Get a membership from the current organization by its unique ID. + + Parameters + ---------- + membership_id : str + Membership ID. + + Returns + ------- + Membership + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/memberships/{membershipId}' + api_params = {} + if membership_id is None: + raise AppwriteException('Missing required parameter: "membership_id"') + + api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Membership) + + + def update_membership( + self, + membership_id: str, + roles: List[str] + ) -> Membership: + """ + Modify the roles of a member in the current organization. + + Parameters + ---------- + membership_id : str + Membership ID. + roles : List[str] + An array of strings. Use this param to set the user's roles in the organization. A role can be any string. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). Maximum of 100 roles are allowed, each 81 characters long. + + Returns + ------- + Membership + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/memberships/{membershipId}' + api_params = {} + if membership_id is None: + raise AppwriteException('Missing required parameter: "membership_id"') + + if roles is None: + raise AppwriteException('Missing required parameter: "roles"') + + api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) + + api_params['roles'] = self._normalize_value(roles) + + response = self.client.call('patch', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Membership) + + + def delete_membership( + self, + membership_id: str + ) -> Dict[str, Any]: + """ + Remove a member from the current organization. The member is removed whether they accepted the invitation or not; a pending invitation is revoked. + + Parameters + ---------- + membership_id : str + Membership ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/memberships/{membershipId}' + api_params = {} + if membership_id is None: + raise AppwriteException('Missing required parameter: "membership_id"') + + api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, api_params) + + return response + + def list_projects( self, queries: Optional[List[str]] = None, @@ -263,7 +612,7 @@ def list_projects( Parameters ---------- queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, teamId, labels, search + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, teamId, labels, search, accessedAt search : Optional[str] Search term to filter your list results. Max length: 256 chars. total : Optional[bool] diff --git a/appwrite/services/project.py b/appwrite/services/project.py index cccde7a9..c9d5c9d4 100644 --- a/appwrite/services/project.py +++ b/appwrite/services/project.py @@ -14,6 +14,7 @@ from ..models.o_auth2_provider_list import OAuth2ProviderList from ..models.o_auth2_amazon import OAuth2Amazon from ..models.o_auth2_apple import OAuth2Apple +from ..models.o_auth2_appwrite import OAuth2Appwrite from ..models.o_auth2_auth0 import OAuth2Auth0 from ..models.o_auth2_authentik import OAuth2Authentik from ..models.o_auth2_autodesk import OAuth2Autodesk @@ -37,6 +38,7 @@ from ..models.o_auth2_linkedin import OAuth2Linkedin from ..models.o_auth2_microsoft import OAuth2Microsoft from ..models.o_auth2_notion import OAuth2Notion +from ..enums.project_o_auth2_oidc_prompt import ProjectOAuth2OidcPrompt from ..models.o_auth2_oidc import OAuth2Oidc from ..models.o_auth2_okta import OAuth2Okta from ..models.o_auth2_paypal import OAuth2Paypal @@ -254,7 +256,7 @@ def create_key( name : str Key name. Max length: 128 chars. scopes : List[ProjectKeyScopes] - Key scopes list. Maximum of 100 scopes are allowed. + Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. @@ -308,7 +310,7 @@ def create_ephemeral_key( Parameters ---------- scopes : List[ProjectKeyScopes] - Key scopes list. Maximum of 100 scopes are allowed. + Key scopes list. Maximum of 200 scopes are allowed. duration : float Time in seconds before ephemeral key expires. Maximum duration is 3600 seconds. @@ -400,7 +402,7 @@ def update_key( name : str Key name. Max length: 128 chars. scopes : List[ProjectKeyScopes] - Key scopes list. Maximum of 100 scopes are allowed. + Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. @@ -790,7 +792,8 @@ def update_o_auth2_server( verification_url: Optional[str] = None, user_code_length: Optional[float] = None, user_code_format: Optional[str] = None, - device_code_duration: Optional[float] = None + device_code_duration: Optional[float] = None, + default_scopes: Optional[List[str]] = None ) -> ProjectModel: """ Update the OAuth2 server (OIDC provider) configuration. @@ -823,6 +826,8 @@ def update_o_auth2_server( Character set for device flow user codes: `numeric` (digits only — best for numeric keypads and TV remotes), `alphabetic` (letters only), or `alphanumeric` (letters and digits — highest entropy per character). Defaults to `alphanumeric`. device_code_duration : Optional[float] Lifetime in seconds of device flow device codes and user codes. Device codes are intentionally short-lived. Leave empty to use default 600. + default_scopes : Optional[List[str]] + List of OAuth2 scopes used when an authorization request omits the scope parameter. Every default scope must also be allowed by the OAuth2 server. Maximum of 100 scopes are allowed, each up to 128 characters long. Returns ------- @@ -861,6 +866,8 @@ def update_o_auth2_server( if user_code_format is not None: api_params['userCodeFormat'] = self._normalize_value(user_code_format) api_params['deviceCodeDuration'] = self._normalize_value(device_code_duration) + if default_scopes is not None: + api_params['defaultScopes'] = self._normalize_value(default_scopes) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -969,6 +976,51 @@ def update_o_auth2_apple( return self._parse_response(response, model=OAuth2Apple) + def update_o_auth2_appwrite( + self, + client_id: Optional[str] = None, + client_secret: Optional[str] = None, + enabled: Optional[bool] = None + ) -> OAuth2Appwrite: + """ + Update the project OAuth2 Appwrite configuration. + + Parameters + ---------- + client_id : Optional[str] + 'Client ID' of Appwrite OAuth2 app. For example: 6a42000000000000b5a0 + client_secret : Optional[str] + 'Client Secret' of Appwrite OAuth2 app. For example: b86afd000000000000000000000000000000000000000000000000000ced5f93 + enabled : Optional[bool] + OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. + + Returns + ------- + OAuth2Appwrite + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/project/oauth2/appwrite' + api_params = {} + + api_params['clientId'] = self._normalize_value(client_id) + api_params['clientSecret'] = self._normalize_value(client_secret) + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call('patch', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=OAuth2Appwrite) + + def update_o_auth2_auth0( self, client_id: Optional[str] = None, @@ -1999,6 +2051,8 @@ def update_o_auth2_oidc( authorization_url: Optional[str] = None, token_url: Optional[str] = None, user_info_url: Optional[str] = None, + prompt: Optional[List[ProjectOAuth2OidcPrompt]] = None, + max_age: Optional[float] = None, enabled: Optional[bool] = None ) -> OAuth2Oidc: """ @@ -2018,6 +2072,10 @@ def update_o_auth2_oidc( OpenID Connect token endpoint URL. Required when wellKnownURL is not provided. For example: https://myoauth.com/oauth2/token user_info_url : Optional[str] OpenID Connect user info endpoint URL. Required when wellKnownURL is not provided. For example: https://myoauth.com/oauth2/userinfo + prompt : Optional[List[ProjectOAuth2OidcPrompt]] + Array of OpenID Connect prompt values controlling the authentication and consent screens. If "none" is included, it must be the only element. "none" means: don't display any authentication or consent screens. "login" means: prompt the user to re-authenticate. "consent" means: prompt the user for consent. "select_account" means: prompt the user to select an account. + max_age : Optional[float] + Maximum authentication age in seconds. When set, the user must have authenticated within this many seconds, otherwise they are prompted to re-authenticate. enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. @@ -2041,6 +2099,8 @@ def update_o_auth2_oidc( api_params['authorizationURL'] = self._normalize_value(authorization_url) api_params['tokenURL'] = self._normalize_value(token_url) api_params['userInfoURL'] = self._normalize_value(user_info_url) + api_params['prompt'] = self._normalize_value(prompt) + api_params['maxAge'] = self._normalize_value(max_age) api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { diff --git a/appwrite/services/sites.py b/appwrite/services/sites.py index ce0c23f1..4daf161f 100644 --- a/appwrite/services/sites.py +++ b/appwrite/services/sites.py @@ -258,11 +258,17 @@ def list_frameworks( def list_specifications( - self + self, + type: Optional[str] = None ) -> SpecificationList: """ List allowed site specifications for this instance. + Parameters + ---------- + type : Optional[str] + Specification type to list. Can be one of: runtimes, builds. + Returns ------- SpecificationList @@ -277,6 +283,9 @@ def list_specifications( api_path = '/sites/specifications' api_params = {} + if type is not None: + api_params['type'] = self._normalize_value(type) + response = self.client.call('get', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), 'accept': 'application/json', @@ -460,8 +469,7 @@ def update( api_params['providerRootDirectory'] = self._normalize_value(provider_root_directory) api_params['providerBranches'] = self._normalize_value(provider_branches) api_params['providerPaths'] = self._normalize_value(provider_paths) - if build_specification is not None: - api_params['buildSpecification'] = self._normalize_value(build_specification) + api_params['buildSpecification'] = self._normalize_value(build_specification) if runtime_specification is not None: api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: diff --git a/appwrite/services/tables_db.py b/appwrite/services/tables_db.py index 7ea86989..9733bc96 100644 --- a/appwrite/services/tables_db.py +++ b/appwrite/services/tables_db.py @@ -96,7 +96,7 @@ def create( database_id: str, name: str, enabled: Optional[bool] = None, - dedicated_database_id: Optional[str] = None + specification: Optional[str] = None ) -> Database: """ Create a new Database. @@ -110,8 +110,8 @@ def create( Database name. Max length: 128 chars. enabled : Optional[bool] Is the database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. - dedicated_database_id : Optional[str] - Optional dedicated database (compute) ID to attach this database to. Leave empty to create a database on the shared pool. + specification : Optional[str] + Database specification. Defaults to `serverless`, which creates the database on the shared pool. Any other value provisions a dedicated database on that specification. Returns ------- @@ -137,8 +137,8 @@ def create( api_params['name'] = self._normalize_value(name) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - if dedicated_database_id is not None: - api_params['dedicatedDatabaseId'] = self._normalize_value(dedicated_database_id) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/usage.py b/appwrite/services/usage.py deleted file mode 100644 index de300c7f..00000000 --- a/appwrite/services/usage.py +++ /dev/null @@ -1,202 +0,0 @@ -from ..service import Service -from urllib.parse import quote -from typing import Any, Dict, List, Optional, Union -from ..exception import AppwriteException -from appwrite.utils.deprecated import deprecated -from ..models.usage_event_list import UsageEventList -from ..models.usage_gauge_list import UsageGaugeList - -class Usage(Service): - - def __init__(self, client) -> None: - super(Usage, self).__init__(client) - - def list_events( - self, - metrics: List[str], - resource: Optional[str] = None, - resource_id: Optional[str] = None, - interval: Optional[str] = None, - dimensions: Optional[List[str]] = None, - start_at: Optional[str] = None, - end_at: Optional[str] = None, - order_by: Optional[str] = None, - order_dir: Optional[str] = None, - limit: Optional[float] = None, - offset: Optional[float] = None - ) -> UsageEventList: - """ - Aggregate usage event metrics. `metrics[]` (1-10) is required; the response always contains one entry per requested metric, each with its own `points[]` time series. - - **Two response shapes**: - - Omit `interval` for a flat top-N table — one point per dimension combination, no time axis. Useful for "top 10 paths by bandwidth in the last 7 days". - - Pass `interval` (`1m`, `15m`, `30m`, `1h`, `1d`) for a time series — one point per (time bucket × dimension combination). - - `dimensions[]` breaks each point down by one or more attributes (service, path, status, country, …). Pass multiple metrics to render stacked charts in one round-trip. `resource` and `resourceId` filter the underlying events. `orderBy=value`+`orderDir=desc`+`limit=N` returns the top-N by aggregated value. When `startAt` is omitted, the default window adapts to `interval` (or 7d when interval is omitted). - - Parameters - ---------- - metrics : List[str] - One to ten metric names. Single-metric callers pass a one-element array. Example: `metrics[]=executions` or `metrics[]=executions&metrics[]=executions.compute` for stacked charts. - resource : Optional[str] - Resource type filter (singular form). Common values: function, site, database, bucket, file, webhook, team, user, project. - resource_id : Optional[str] - Resource id filter. - interval : Optional[str] - Time interval size. Omit (null) for a flat aggregate over the whole window. Allowed: 1m, 15m, 30m, 1h, 1d. - dimensions : Optional[List[str]] - Break-down dimensions (max 10). Allowed: path, method, status, service, country, region, hostname, osName, clientType, clientName, deviceName, teamId, resourceId. - start_at : Optional[str] - Range start in ISO 8601. Defaults adapt to interval (7d for the no-interval aggregate). - end_at : Optional[str] - Range end in ISO 8601. Defaults to the current time. - order_by : Optional[str] - Column to order by. Allowed: time, value. Default time when an interval is set; otherwise value. - order_dir : Optional[str] - Sort direction: asc or desc. Default desc — paired with the default limit, returns the most recent / highest-value groups first. - limit : Optional[float] - Maximum rows to return (1-5000). - offset : Optional[float] - Pagination offset (0-100000). - - Returns - ------- - UsageEventList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/usage/events' - api_params = {} - if metrics is None: - raise AppwriteException('Missing required parameter: "metrics"') - - - api_params['metrics'] = self._normalize_value(metrics) - if resource is not None: - api_params['resource'] = self._normalize_value(resource) - if resource_id is not None: - api_params['resourceId'] = self._normalize_value(resource_id) - if interval is not None: - api_params['interval'] = self._normalize_value(interval) - if dimensions is not None: - api_params['dimensions'] = self._normalize_value(dimensions) - if start_at is not None: - api_params['startAt'] = self._normalize_value(start_at) - if end_at is not None: - api_params['endAt'] = self._normalize_value(end_at) - if order_by is not None: - api_params['orderBy'] = self._normalize_value(order_by) - if order_dir is not None: - api_params['orderDir'] = self._normalize_value(order_dir) - if limit is not None: - api_params['limit'] = self._normalize_value(limit) - if offset is not None: - api_params['offset'] = self._normalize_value(offset) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=UsageEventList) - - - def list_gauges( - self, - metrics: List[str], - resource_id: Optional[str] = None, - team_id: Optional[str] = None, - interval: Optional[str] = None, - dimensions: Optional[List[str]] = None, - start_at: Optional[str] = None, - end_at: Optional[str] = None, - order_by: Optional[str] = None, - order_dir: Optional[str] = None, - limit: Optional[float] = None, - offset: Optional[float] = None - ) -> UsageGaugeList: - """ - Aggregate usage gauge snapshots. Gauges are point-in-time values (storage totals, resource counts, …); each point carries the latest snapshot in its interval via `argMax(value, time)`. `metrics[]` (1-10) is required; the response always contains one entry per requested metric, each with its own `points[]` time series. - - **Two response shapes**: - - Omit `interval` for a flat top-N table — `argMax(value, time)` per dimension combination over the whole window, no time axis. Useful for "top 10 resources by current storage". - - Pass `interval` (`1m`, `15m`, `30m`, `1h`, `1d`) for a time series — one snapshot per (time bucket × dimension combination). - - `dimensions[]` breaks each point down further. Supported on gauges: `resourceId`, `teamId`, `service`, `resource`. `service` and `resource` enable per-service / per-resource-type panels (e.g. storage-by-service: group `files.storage`, `deployments.storage`, `builds.storage`, `databases.storage` by `service`). Pass multiple metrics to render stacked charts in one round-trip. `resourceId` and `teamId` parameters filter the underlying rows. `orderBy=value`+`orderDir=desc`+`limit=N` returns the top-N. When `startAt` is omitted, the default window adapts to interval (or 7d when interval is omitted). - - Parameters - ---------- - metrics : List[str] - One to ten metric names. Single-metric callers pass a one-element array. Example: `metrics[]=files.storage` or `metrics[]=files.storage&metrics[]=deployments.storage` for stacked charts. - resource_id : Optional[str] - Resource id filter. - team_id : Optional[str] - Team id filter. - interval : Optional[str] - Time interval size. Omit (null) for a flat aggregate over the whole window. Allowed: 1m, 15m, 30m, 1h, 1d. - dimensions : Optional[List[str]] - Break-down dimensions. Allowed: resourceId, teamId, service, resource. - start_at : Optional[str] - Range start in ISO 8601. Defaults to endAt - 7d. - end_at : Optional[str] - Range end in ISO 8601. Defaults to the current time. - order_by : Optional[str] - Column to order by. Allowed: time, value. Default time. - order_dir : Optional[str] - Sort direction: asc or desc. Default desc — paired with the default limit, this returns the most recent groups first. Pass asc for chronological charting. - limit : Optional[float] - Maximum rows to return (1-5000). - offset : Optional[float] - Pagination offset (0-100000). - - Returns - ------- - UsageGaugeList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/usage/gauges' - api_params = {} - if metrics is None: - raise AppwriteException('Missing required parameter: "metrics"') - - - api_params['metrics'] = self._normalize_value(metrics) - if resource_id is not None: - api_params['resourceId'] = self._normalize_value(resource_id) - if team_id is not None: - api_params['teamId'] = self._normalize_value(team_id) - if interval is not None: - api_params['interval'] = self._normalize_value(interval) - if dimensions is not None: - api_params['dimensions'] = self._normalize_value(dimensions) - if start_at is not None: - api_params['startAt'] = self._normalize_value(start_at) - if end_at is not None: - api_params['endAt'] = self._normalize_value(end_at) - if order_by is not None: - api_params['orderBy'] = self._normalize_value(order_by) - if order_dir is not None: - api_params['orderDir'] = self._normalize_value(order_dir) - if limit is not None: - api_params['limit'] = self._normalize_value(limit) - if offset is not None: - api_params['offset'] = self._normalize_value(offset) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=UsageGaugeList) - diff --git a/appwrite/services/users.py b/appwrite/services/users.py index 00bd630f..c0e282e6 100644 --- a/appwrite/services/users.py +++ b/appwrite/services/users.py @@ -41,7 +41,7 @@ def list( Parameters ---------- queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, email, phone, status, passwordUpdate, registration, emailVerification, phoneVerification, labels, impersonator + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, email, phone, status, passwordUpdate, registration, emailVerification, phoneVerification, labels, impersonator, accessedAt search : Optional[str] Search term to filter your list results. Max length: 256 chars. total : Optional[bool] diff --git a/docs/examples/health/get-audits-db.md b/docs/examples/apps/update-labels.md similarity index 63% rename from docs/examples/health/get-audits-db.md rename to docs/examples/apps/update-labels.md index 774edec1..0601df3f 100644 --- a/docs/examples/health/get-audits-db.md +++ b/docs/examples/apps/update-labels.md @@ -1,16 +1,19 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatusList +from appwrite.services.apps import Apps +from appwrite.models import App client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +apps = Apps(client) -result: HealthStatusList = health.get_audits_db() +result: App = apps.update_labels( + app_id = '', + labels = [] +) print(result.model_dump()) ``` diff --git a/docs/examples/backups/create-restoration.md b/docs/examples/backups/create-restoration.md index e2966caa..03f3f0a9 100644 --- a/docs/examples/backups/create-restoration.md +++ b/docs/examples/backups/create-restoration.md @@ -15,7 +15,8 @@ result: BackupRestoration = backups.create_restoration( archive_id = '', services = [BackupServices.DATABASES], new_resource_id = '', # optional - new_resource_name = '' # optional + new_resource_name = '', # optional + new_specification = 'serverless' # optional ) print(result.model_dump()) diff --git a/docs/examples/functions/get-deployment-download.md b/docs/examples/functions/get-deployment-download.md index 7f6b2f6b..49df861b 100644 --- a/docs/examples/functions/get-deployment-download.md +++ b/docs/examples/functions/get-deployment-download.md @@ -13,6 +13,7 @@ functions = Functions(client) result: bytes = functions.get_deployment_download( function_id = '', deployment_id = '', - type = DeploymentDownloadType.SOURCE # optional + type = DeploymentDownloadType.SOURCE, # optional + token = '' # optional ) ``` diff --git a/docs/examples/functions/list-specifications.md b/docs/examples/functions/list-specifications.md index 5b76860d..7cf529a9 100644 --- a/docs/examples/functions/list-specifications.md +++ b/docs/examples/functions/list-specifications.md @@ -10,7 +10,9 @@ client.set_key('') # Your secret API key functions = Functions(client) -result: SpecificationList = functions.list_specifications() +result: SpecificationList = functions.list_specifications( + type = 'runtimes' # optional +) print(result.model_dump()) ``` diff --git a/docs/examples/health/get-antivirus.md b/docs/examples/health/get-antivirus.md deleted file mode 100644 index 1ab51503..00000000 --- a/docs/examples/health/get-antivirus.md +++ /dev/null @@ -1,16 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthAntivirus - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthAntivirus = health.get_antivirus() - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-certificate.md b/docs/examples/health/get-certificate.md deleted file mode 100644 index 53dde7fb..00000000 --- a/docs/examples/health/get-certificate.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthCertificate - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthCertificate = health.get_certificate( - domain = '' # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-db.md b/docs/examples/health/get-db.md deleted file mode 100644 index 47b6dd98..00000000 --- a/docs/examples/health/get-db.md +++ /dev/null @@ -1,16 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatusList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthStatusList = health.get_db() - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-failed-jobs.md b/docs/examples/health/get-failed-jobs.md deleted file mode 100644 index da08c619..00000000 --- a/docs/examples/health/get-failed-jobs.md +++ /dev/null @@ -1,20 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue -from appwrite.enums import HealthQueueName - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_failed_jobs( - name = HealthQueueName.V1_DATABASE, - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-pub-sub.md b/docs/examples/health/get-pub-sub.md deleted file mode 100644 index 588a2bac..00000000 --- a/docs/examples/health/get-pub-sub.md +++ /dev/null @@ -1,16 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatusList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthStatusList = health.get_pub_sub() - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-certificates.md b/docs/examples/health/get-queue-certificates.md deleted file mode 100644 index 6666463f..00000000 --- a/docs/examples/health/get-queue-certificates.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_certificates( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-databases.md b/docs/examples/health/get-queue-databases.md deleted file mode 100644 index 44e165ed..00000000 --- a/docs/examples/health/get-queue-databases.md +++ /dev/null @@ -1,19 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_databases( - name = '', # optional - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-deletes.md b/docs/examples/health/get-queue-deletes.md deleted file mode 100644 index fece6301..00000000 --- a/docs/examples/health/get-queue-deletes.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_deletes( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-functions.md b/docs/examples/health/get-queue-functions.md deleted file mode 100644 index 03d9afe8..00000000 --- a/docs/examples/health/get-queue-functions.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_functions( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-logs.md b/docs/examples/health/get-queue-logs.md deleted file mode 100644 index 5191fa5a..00000000 --- a/docs/examples/health/get-queue-logs.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_logs( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-mails.md b/docs/examples/health/get-queue-mails.md deleted file mode 100644 index aed05e1d..00000000 --- a/docs/examples/health/get-queue-mails.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_mails( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-messaging.md b/docs/examples/health/get-queue-messaging.md deleted file mode 100644 index 5da876a6..00000000 --- a/docs/examples/health/get-queue-messaging.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_messaging( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-migrations.md b/docs/examples/health/get-queue-migrations.md deleted file mode 100644 index 749675d7..00000000 --- a/docs/examples/health/get-queue-migrations.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_migrations( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-stats-resources.md b/docs/examples/health/get-queue-stats-resources.md deleted file mode 100644 index 60c0dd57..00000000 --- a/docs/examples/health/get-queue-stats-resources.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_stats_resources( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-usage.md b/docs/examples/health/get-queue-usage.md deleted file mode 100644 index 10fa4a0f..00000000 --- a/docs/examples/health/get-queue-usage.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_usage( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-queue-webhooks.md b/docs/examples/health/get-queue-webhooks.md deleted file mode 100644 index 24423761..00000000 --- a/docs/examples/health/get-queue-webhooks.md +++ /dev/null @@ -1,18 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthQueue = health.get_queue_webhooks( - threshold = None # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-storage-local.md b/docs/examples/health/get-storage-local.md deleted file mode 100644 index 57b8ec40..00000000 --- a/docs/examples/health/get-storage-local.md +++ /dev/null @@ -1,16 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatus - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthStatus = health.get_storage_local() - -print(result.model_dump()) -``` diff --git a/docs/examples/health/get-storage.md b/docs/examples/health/get-storage.md deleted file mode 100644 index a17ee4e3..00000000 --- a/docs/examples/health/get-storage.md +++ /dev/null @@ -1,16 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatus - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -health = Health(client) - -result: HealthStatus = health.get_storage() - -print(result.model_dump()) -``` diff --git a/docs/examples/messaging/list-provider-logs.md b/docs/examples/messaging/list-provider-logs.md deleted file mode 100644 index ad271428..00000000 --- a/docs/examples/messaging/list-provider-logs.md +++ /dev/null @@ -1,20 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.messaging import Messaging -from appwrite.models import LogList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -messaging = Messaging(client) - -result: LogList = messaging.list_provider_logs( - provider_id = '', - queries = [], # optional - total = False # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/messaging/list-subscriber-logs.md b/docs/examples/messaging/list-subscriber-logs.md deleted file mode 100644 index b02c2b1b..00000000 --- a/docs/examples/messaging/list-subscriber-logs.md +++ /dev/null @@ -1,20 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.messaging import Messaging -from appwrite.models import LogList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -messaging = Messaging(client) - -result: LogList = messaging.list_subscriber_logs( - subscriber_id = '', - queries = [], # optional - total = False # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/messaging/list-topic-logs.md b/docs/examples/messaging/list-topic-logs.md deleted file mode 100644 index 3ed2d7e3..00000000 --- a/docs/examples/messaging/list-topic-logs.md +++ /dev/null @@ -1,20 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.messaging import Messaging -from appwrite.models import LogList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -messaging = Messaging(client) - -result: LogList = messaging.list_topic_logs( - topic_id = '', - queries = [], # optional - total = False # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/oauth2/approve.md b/docs/examples/oauth2/approve.md index b3313599..12bc9c0d 100644 --- a/docs/examples/oauth2/approve.md +++ b/docs/examples/oauth2/approve.md @@ -12,7 +12,8 @@ oauth2 = Oauth2(client) result: Oauth2Approve = oauth2.approve( grant_id = '', - authorization_details = '' # optional + authorization_details = '', # optional + scope = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/oauth2/authorize.md b/docs/examples/oauth2/authorize.md index 3ea83a66..9d7bb486 100644 --- a/docs/examples/oauth2/authorize.md +++ b/docs/examples/oauth2/authorize.md @@ -11,17 +11,20 @@ client.set_project('') # Your project ID oauth2 = Oauth2(client) result: Oauth2Authorize = oauth2.authorize( - client_id = '', - redirect_uri = 'https://example.com', - response_type = 'code', - scope = '', + client_id = '', # optional + redirect_uri = 'https://example.com', # optional + response_type = '', # optional + scope = '', # optional state = '', # optional nonce = '', # optional code_challenge = '', # optional code_challenge_method = 's256', # optional prompt = '', # optional max_age = 0, # optional - authorization_details = '' # optional + authorization_details = '', # optional + resource = '', # optional + audience = '', # optional + request_uri = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/oauth2/create-device-authorization.md b/docs/examples/oauth2/create-device-authorization.md index 4ba20f77..0fa3852d 100644 --- a/docs/examples/oauth2/create-device-authorization.md +++ b/docs/examples/oauth2/create-device-authorization.md @@ -13,7 +13,9 @@ oauth2 = Oauth2(client) result: Oauth2DeviceAuthorization = oauth2.create_device_authorization( client_id = '', # optional scope = '', # optional - authorization_details = '' # optional + authorization_details = '', # optional + resource = '', # optional + audience = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/oauth2/create-par.md b/docs/examples/oauth2/create-par.md new file mode 100644 index 00000000..2018794c --- /dev/null +++ b/docs/examples/oauth2/create-par.md @@ -0,0 +1,30 @@ +```python +from appwrite.client import Client +from appwrite.services.oauth2 import Oauth2 +from appwrite.models import Oauth2PAR + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_session('') # The user session to authenticate with +client.set_project('') # Your project ID + +oauth2 = Oauth2(client) + +result: Oauth2PAR = oauth2.create_par( + client_id = '', + redirect_uri = 'https://example.com', + response_type = 'code', + scope = '', # optional + state = '', # optional + nonce = '', # optional + code_challenge = '', # optional + code_challenge_method = 's256', # optional + prompt = '', # optional + max_age = 0, # optional + authorization_details = '', # optional + resource = '', # optional + audience = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/oauth2/create-token.md b/docs/examples/oauth2/create-token.md index ac698593..1d52bbc9 100644 --- a/docs/examples/oauth2/create-token.md +++ b/docs/examples/oauth2/create-token.md @@ -18,7 +18,9 @@ result: Oauth2Token = oauth2.create_token( client_id = '', # optional client_secret = '', # optional code_verifier = '', # optional - redirect_uri = 'https://example.com' # optional + redirect_uri = 'https://example.com', # optional + resource = '', # optional + audience = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/oauth2/list-organizations.md b/docs/examples/oauth2/list-organizations.md new file mode 100644 index 00000000..42ece3a8 --- /dev/null +++ b/docs/examples/oauth2/list-organizations.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.oauth2 import Oauth2 +from appwrite.models import Oauth2OrganizationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_session('') # The user session to authenticate with +client.set_project('') # Your project ID + +oauth2 = Oauth2(client) + +result: Oauth2OrganizationList = oauth2.list_organizations( + limit = 1, # optional + offset = 0, # optional + search = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/oauth2/list-projects.md b/docs/examples/oauth2/list-projects.md new file mode 100644 index 00000000..97a58b7b --- /dev/null +++ b/docs/examples/oauth2/list-projects.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.oauth2 import Oauth2 +from appwrite.models import Oauth2ProjectList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_session('') # The user session to authenticate with +client.set_project('') # Your project ID + +oauth2 = Oauth2(client) + +result: Oauth2ProjectList = oauth2.list_projects( + limit = 1, # optional + offset = 0, # optional + search = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/organization/create-membership.md b/docs/examples/organization/create-membership.md new file mode 100644 index 00000000..0801bdd7 --- /dev/null +++ b/docs/examples/organization/create-membership.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization +from appwrite.models import Membership + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +organization = Organization(client) + +result: Membership = organization.create_membership( + roles = [], + email = 'email@example.com', # optional + user_id = '', # optional + phone = '+12065550100', # optional + url = 'https://example.com', # optional + name = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/health/get.md b/docs/examples/organization/delete-membership.md similarity index 60% rename from docs/examples/health/get.md rename to docs/examples/organization/delete-membership.md index 5a3b3d06..dee81d19 100644 --- a/docs/examples/health/get.md +++ b/docs/examples/organization/delete-membership.md @@ -1,16 +1,15 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatus +from appwrite.services.organization import Organization client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthStatus = health.get() - -print(result.model_dump()) +result = organization.delete_membership( + membership_id = '' +) ``` diff --git a/docs/examples/health/get-time.md b/docs/examples/organization/delete.md similarity index 60% rename from docs/examples/health/get-time.md rename to docs/examples/organization/delete.md index 5ffae25e..94b7c2a7 100644 --- a/docs/examples/health/get-time.md +++ b/docs/examples/organization/delete.md @@ -1,16 +1,13 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthTime +from appwrite.services.organization import Organization client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthTime = health.get_time() - -print(result.model_dump()) +result = organization.delete() ``` diff --git a/docs/examples/health/get-queue-audits.md b/docs/examples/organization/get-membership.md similarity index 57% rename from docs/examples/health/get-queue-audits.md rename to docs/examples/organization/get-membership.md index a892ca25..b3fcd9de 100644 --- a/docs/examples/health/get-queue-audits.md +++ b/docs/examples/organization/get-membership.md @@ -1,17 +1,17 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue +from appwrite.services.organization import Organization +from appwrite.models import Membership client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthQueue = health.get_queue_audits( - threshold = None # optional +result: Membership = organization.get_membership( + membership_id = '' ) print(result.model_dump()) diff --git a/docs/examples/health/get-cache.md b/docs/examples/organization/get.md similarity index 59% rename from docs/examples/health/get-cache.md rename to docs/examples/organization/get.md index 39050878..b99b6a7f 100644 --- a/docs/examples/health/get-cache.md +++ b/docs/examples/organization/get.md @@ -1,16 +1,16 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatusList +from appwrite.services.organization import Organization +from appwrite.models import Organization as OrganizationModel client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthStatusList = health.get_cache() +result: OrganizationModel = organization.get() print(result.model_dump()) ``` diff --git a/docs/examples/messaging/list-message-logs.md b/docs/examples/organization/list-memberships.md similarity index 60% rename from docs/examples/messaging/list-message-logs.md rename to docs/examples/organization/list-memberships.md index 27d6b9b6..e49e1793 100644 --- a/docs/examples/messaging/list-message-logs.md +++ b/docs/examples/organization/list-memberships.md @@ -1,18 +1,18 @@ ```python from appwrite.client import Client -from appwrite.services.messaging import Messaging -from appwrite.models import LogList +from appwrite.services.organization import Organization +from appwrite.models import MembershipList client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -messaging = Messaging(client) +organization = Organization(client) -result: LogList = messaging.list_message_logs( - message_id = '', +result: MembershipList = organization.list_memberships( queries = [], # optional + search = '', # optional total = False # optional ) diff --git a/docs/examples/health/get-console-pausing.md b/docs/examples/organization/update-membership.md similarity index 55% rename from docs/examples/health/get-console-pausing.md rename to docs/examples/organization/update-membership.md index 633c175a..a4f9c5a0 100644 --- a/docs/examples/health/get-console-pausing.md +++ b/docs/examples/organization/update-membership.md @@ -1,18 +1,18 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthStatus +from appwrite.services.organization import Organization +from appwrite.models import Membership client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthStatus = health.get_console_pausing( - threshold = None, # optional - inactivity_days = None # optional +result: Membership = organization.update_membership( + membership_id = '', + roles = [] ) print(result.model_dump()) diff --git a/docs/examples/health/get-queue-builds.md b/docs/examples/organization/update.md similarity index 56% rename from docs/examples/health/get-queue-builds.md rename to docs/examples/organization/update.md index 0ae87b2c..6d456c57 100644 --- a/docs/examples/health/get-queue-builds.md +++ b/docs/examples/organization/update.md @@ -1,17 +1,17 @@ ```python from appwrite.client import Client -from appwrite.services.health import Health -from appwrite.models import HealthQueue +from appwrite.services.organization import Organization +from appwrite.models import Organization as OrganizationModel client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_key('') # Your secret API key -health = Health(client) +organization = Organization(client) -result: HealthQueue = health.get_queue_builds( - threshold = None # optional +result: OrganizationModel = organization.update( + name = '' ) print(result.model_dump()) diff --git a/docs/examples/project/update-o-auth-2-appwrite.md b/docs/examples/project/update-o-auth-2-appwrite.md new file mode 100644 index 00000000..7b765921 --- /dev/null +++ b/docs/examples/project/update-o-auth-2-appwrite.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.project import Project +from appwrite.models import OAuth2Appwrite + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +project = Project(client) + +result: OAuth2Appwrite = project.update_o_auth2_appwrite( + client_id = '', # optional + client_secret = '', # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/project/update-o-auth-2-oidc.md b/docs/examples/project/update-o-auth-2-oidc.md index 3913262d..e2df2e3c 100644 --- a/docs/examples/project/update-o-auth-2-oidc.md +++ b/docs/examples/project/update-o-auth-2-oidc.md @@ -2,6 +2,7 @@ from appwrite.client import Client from appwrite.services.project import Project from appwrite.models import OAuth2Oidc +from appwrite.enums import ProjectOAuth2OidcPrompt client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint @@ -17,6 +18,8 @@ result: OAuth2Oidc = project.update_o_auth2_oidc( authorization_url = 'https://example.com', # optional token_url = 'https://example.com', # optional user_info_url = 'https://example.com', # optional + prompt = [ProjectOAuth2OidcPrompt.NONE], # optional + max_age = 0, # optional enabled = False # optional ) diff --git a/docs/examples/project/update-o-auth-2-server.md b/docs/examples/project/update-o-auth-2-server.md index 6c5b2578..6be24c54 100644 --- a/docs/examples/project/update-o-auth-2-server.md +++ b/docs/examples/project/update-o-auth-2-server.md @@ -23,7 +23,8 @@ result: ProjectModel = project.update_o_auth2_server( verification_url = 'https://example.com', # optional user_code_length = 6, # optional user_code_format = 'numeric', # optional - device_code_duration = 60 # optional + device_code_duration = 60, # optional + default_scopes = [] # optional ) print(result.model_dump()) diff --git a/docs/examples/sites/list-specifications.md b/docs/examples/sites/list-specifications.md index c1229a30..2f04ddf4 100644 --- a/docs/examples/sites/list-specifications.md +++ b/docs/examples/sites/list-specifications.md @@ -10,7 +10,9 @@ client.set_key('') # Your secret API key sites = Sites(client) -result: SpecificationList = sites.list_specifications() +result: SpecificationList = sites.list_specifications( + type = 'runtimes' # optional +) print(result.model_dump()) ``` diff --git a/docs/examples/tablesdb/create.md b/docs/examples/tablesdb/create.md index c50f28e7..a816905f 100644 --- a/docs/examples/tablesdb/create.md +++ b/docs/examples/tablesdb/create.md @@ -14,7 +14,7 @@ result: Database = tables_db.create( database_id = '', name = '', enabled = False, # optional - dedicated_database_id = '' # optional + specification = 'serverless' # optional ) print(result.model_dump()) diff --git a/docs/examples/usage/list-events.md b/docs/examples/usage/list-events.md deleted file mode 100644 index 83f8d725..00000000 --- a/docs/examples/usage/list-events.md +++ /dev/null @@ -1,28 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.usage import Usage -from appwrite.models import UsageEventList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -usage = Usage(client) - -result: UsageEventList = usage.list_events( - metrics = [], - resource = '', # optional - resource_id = '', # optional - interval = '1m', # optional - dimensions = [], # optional - start_at = '2020-10-15T06:38:00.000+00:00', # optional - end_at = '2020-10-15T06:38:00.000+00:00', # optional - order_by = 'time', # optional - order_dir = 'asc', # optional - limit = 1, # optional - offset = 0 # optional -) - -print(result.model_dump()) -``` diff --git a/docs/examples/usage/list-gauges.md b/docs/examples/usage/list-gauges.md deleted file mode 100644 index fb221f9a..00000000 --- a/docs/examples/usage/list-gauges.md +++ /dev/null @@ -1,28 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.usage import Usage -from appwrite.models import UsageGaugeList - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -usage = Usage(client) - -result: UsageGaugeList = usage.list_gauges( - metrics = [], - resource_id = '', # optional - team_id = '', # optional - interval = '1m', # optional - dimensions = [], # optional - start_at = '2020-10-15T06:38:00.000+00:00', # optional - end_at = '2020-10-15T06:38:00.000+00:00', # optional - order_by = 'time', # optional - order_dir = 'asc', # optional - limit = 1, # optional - offset = 0 # optional -) - -print(result.model_dump()) -``` diff --git a/pyproject.toml b/pyproject.toml index 64acd0d7..10559426 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "21.0.0" +version = "22.0.0" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" diff --git a/requirements.txt b/requirements.txt index 43f14202..b3386211 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,3 +1,3 @@ requests>=2.31,<3 -requests_mock==1.11.0 +requests_mock==1.12.1 pydantic>=2,<3 diff --git a/setup.py b/setup.py index bedddde5..9557066e 100644 --- a/setup.py +++ b/setup.py @@ -8,7 +8,7 @@ setuptools.setup( name = 'appwrite', packages = setuptools.find_packages(), - version = '21.0.0', + version = '22.0.0', license='BSD-3-Clause', description = 'Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', long_description = long_description, @@ -18,7 +18,7 @@ maintainer = 'Appwrite Team', maintainer_email = 'team@appwrite.io', url = 'https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/21.0.0.tar.gz', + download_url='https://github.com/appwrite/sdk-for-python/archive/22.0.0.tar.gz', install_requires=[ 'requests', 'pydantic>=2,<3', diff --git a/test/services/test_activities.py b/test/services/test_activities.py index 41d9d8b1..9fcc5e4d 100644 --- a/test/services/test_activities.py +++ b/test/services/test_activities.py @@ -47,9 +47,7 @@ def test_get_event(self, m): "time": "2020-10-15T06:38:00.000+00:00", "projectId": "610fc2f985ee0", "teamId": "610fc2f985ee0", - "hostname": "appwrite.io", - "countryCode": "US", - "countryName": "United States" + "hostname": "appwrite.io" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_apps.py b/test/services/test_apps.py index a8d5984d..4520a42b 100644 --- a/test/services/test_apps.py +++ b/test/services/test_apps.py @@ -42,6 +42,7 @@ def test_create(self, m): "contacts": [], "tagline": "Automate your workspace.", "tags": [], + "labels": [], "images": [], "supportUrl": "https:\/\/example.com\/support", "dataDeletionUrl": "https:\/\/example.com\/data-deletion", @@ -80,6 +81,7 @@ def test_get(self, m): "contacts": [], "tagline": "Automate your workspace.", "tags": [], + "labels": [], "images": [], "supportUrl": "https:\/\/example.com\/support", "dataDeletionUrl": "https:\/\/example.com\/data-deletion", @@ -116,6 +118,7 @@ def test_update(self, m): "contacts": [], "tagline": "Automate your workspace.", "tags": [], + "labels": [], "images": [], "supportUrl": "https:\/\/example.com\/support", "dataDeletionUrl": "https:\/\/example.com\/data-deletion", @@ -150,6 +153,44 @@ def test_delete(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_update_labels(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "secrets": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.update_labels( + '', + [], + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_secrets(self, m): data = { @@ -236,6 +277,7 @@ def test_update_team(self, m): "contacts": [], "tagline": "Automate your workspace.", "tags": [], + "labels": [], "images": [], "supportUrl": "https:\/\/example.com\/support", "dataDeletionUrl": "https:\/\/example.com\/data-deletion", diff --git a/test/services/test_backups.py b/test/services/test_backups.py index 83c59835..dfa1f5a2 100644 --- a/test/services/test_backups.py +++ b/test/services/test_backups.py @@ -196,7 +196,7 @@ def test_create_restoration(self, m): "migrationId": "did8jx6ws45jana098ab7", "services": [], "resources": [], - "options": "{databases.database[{oldId, newId, newName}]}" + "options": "{databases.database[{oldId, newId, newName, newSpecification}]}" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -235,7 +235,7 @@ def test_get_restoration(self, m): "migrationId": "did8jx6ws45jana098ab7", "services": [], "resources": [], - "options": "{databases.database[{oldId, newId, newName}]}" + "options": "{databases.database[{oldId, newId, newName, newSpecification}]}" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_health.py b/test/services/test_health.py deleted file mode 100644 index 930aeb62..00000000 --- a/test/services/test_health.py +++ /dev/null @@ -1,361 +0,0 @@ -import json -import requests_mock -import unittest - -from appwrite.client import Client -from appwrite.input_file import InputFile -from appwrite.models import * -from appwrite.services.health import Health - -class HealthServiceTest(unittest.TestCase): - - def setUp(self): - self.client = Client() - self.health = Health(self.client) - - @requests_mock.Mocker() - def test_get(self, m): - data = { - "name": "database", - "ping": 128.0, - "status": "pass" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_antivirus(self, m): - data = { - "version": "1.0.0", - "status": "online" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_antivirus( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_audits_db(self, m): - data = { - "total": 5.0, - "statuses": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_audits_db( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_cache(self, m): - data = { - "total": 5.0, - "statuses": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_cache( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_certificate(self, m): - data = { - "name": "\/CN=www.google.com", - "subjectSN": "", - "issuerOrganisation": "", - "validFrom": "1704200998", - "validTo": "1711458597", - "signatureTypeSN": "RSA-SHA256" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_certificate( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_console_pausing(self, m): - data = { - "name": "database", - "ping": 128.0, - "status": "pass" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_console_pausing( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_db(self, m): - data = { - "total": 5.0, - "statuses": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_db( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_pub_sub(self, m): - data = { - "total": 5.0, - "statuses": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_pub_sub( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_audits(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_audits( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_builds(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_builds( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_certificates(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_certificates( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_databases(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_databases( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_deletes(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_deletes( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_failed_jobs(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_failed_jobs( - 'v1-database', - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_functions(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_functions( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_logs(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_logs( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_mails(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_mails( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_messaging(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_messaging( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_migrations(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_migrations( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_stats_resources(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_stats_resources( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_usage(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_usage( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_queue_webhooks(self, m): - data = { - "size": 8.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_queue_webhooks( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_storage(self, m): - data = { - "name": "database", - "ping": 128.0, - "status": "pass" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_storage( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_storage_local(self, m): - data = { - "name": "database", - "ping": 128.0, - "status": "pass" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_storage_local( - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_get_time(self, m): - data = { - "remoteTime": 1639490751.0, - "localTime": 1639490844.0, - "diff": 93.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.health.get_time( - ) - - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_messaging.py b/test/services/test_messaging.py index 1424b6a1..ef6d618d 100644 --- a/test/services/test_messaging.py +++ b/test/services/test_messaging.py @@ -250,21 +250,6 @@ def test_delete(self, m): self.assertEqual(response, data) - @requests_mock.Mocker() - def test_list_message_logs(self, m): - data = { - "total": 5.0, - "logs": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_message_logs( - '', - ) - - self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() def test_list_targets(self, m): data = { @@ -974,36 +959,6 @@ def test_delete_provider(self, m): self.assertEqual(response, data) - @requests_mock.Mocker() - def test_list_provider_logs(self, m): - data = { - "total": 5.0, - "logs": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_provider_logs( - '', - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_list_subscriber_logs(self, m): - data = { - "total": 5.0, - "logs": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_subscriber_logs( - '', - ) - - self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() def test_list_topics(self, m): data = { @@ -1094,21 +1049,6 @@ def test_delete_topic(self, m): self.assertEqual(response, data) - @requests_mock.Mocker() - def test_list_topic_logs(self, m): - data = { - "total": 5.0, - "logs": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_topic_logs( - '', - ) - - self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() def test_list_subscribers(self, m): data = { diff --git a/test/services/test_oauth2.py b/test/services/test_oauth2.py index 4096d693..3b0bc38e 100644 --- a/test/services/test_oauth2.py +++ b/test/services/test_oauth2.py @@ -37,10 +37,6 @@ def test_authorize(self, m): m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) response = self.oauth2.authorize( - '', - 'https://example.com', - 'code', - '', ) self.assertEqual(response.to_dict(), data) @@ -72,6 +68,7 @@ def test_create_grant(self, m): "userId": "5e5ea5c16897e", "appId": "5e5ea5c16897e", "scopes": [], + "resources": [], "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", "prompt": "login", "redirectUri": "https:\/\/example.com\/callback", @@ -96,6 +93,7 @@ def test_get_grant(self, m): "userId": "5e5ea5c16897e", "appId": "5e5ea5c16897e", "scopes": [], + "resources": [], "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", "prompt": "login", "redirectUri": "https:\/\/example.com\/callback", @@ -111,6 +109,51 @@ def test_get_grant(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_organizations(self, m): + data = { + "total": 5.0, + "organizations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.oauth2.list_organizations( + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_par(self, m): + data = { + "request_uri": "urn:appwrite:oauth2:request:5e5ea5c16897e", + "expires_in": 600.0 +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.oauth2.create_par( + '', + 'https://example.com', + 'code', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_projects(self, m): + data = { + "total": 5.0, + "projects": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.oauth2.list_projects( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_reject(self, m): data = { diff --git a/test/services/test_organization.py b/test/services/test_organization.py index a4e32d24..7cd67f61 100644 --- a/test/services/test_organization.py +++ b/test/services/test_organization.py @@ -13,6 +13,468 @@ def setUp(self): self.client = Client() self.organization = Organization(self.client) + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + "billingBudget": 50.0, + "budgetAlerts": [], + "billingPlan": "tier-1", + "billingPlanId": "tier-1", + "billingPlanDetails": { + "$id": "tier-0", + "name": "Hobby", + "desc": "Hobby plan", + "order": 0.0, + "price": 25, + "trial": 14.0, + "bandwidth": 25.0, + "storage": 25.0, + "imageTransformations": 100.0, + "screenshotsGenerated": 50.0, + "members": 25.0, + "webhooks": 25.0, + "projects": 2.0, + "platforms": 3.0, + "users": 25.0, + "teams": 25.0, + "databases": 25.0, + "databasesReads": 500000.0, + "databasesWrites": 250000.0, + "databasesBatchSize": 100.0, + "buckets": 25.0, + "fileSize": 25.0, + "functions": 25.0, + "sites": 1.0, + "executions": 25.0, + "executionsRetentionCount": 10000.0, + "GBHours": 100.0, + "realtime": 25.0, + "realtimeMessages": 100000.0, + "messages": 1000.0, + "topics": 1.0, + "authPhone": 10.0, + "domains": 5.0, + "activityLogs": 7.0, + "usageLogs": 30.0, + "projectInactivityDays": 7.0, + "alertLimit": 80.0, + "usage": { + "bandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "executions": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "member": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtime": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtimeMessages": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtimeBandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "storage": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "users": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "GBHours": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "imageTransformations": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "credits": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + } + }, + "addons": { + "seats": { + "supported": True, + "planIncluded": 1.0, + "limit": 5.0, + "type": "numeric", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "projects": { + "supported": True, + "planIncluded": 1.0, + "limit": 5.0, + "type": "numeric", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + } + }, + "budgetCapEnabled": True, + "customSmtp": True, + "emailBranding": True, + "requiresPaymentMethod": True, + "requiresBillingAddress": True, + "isAvailable": True, + "selfService": True, + "premiumSupport": True, + "budgeting": True, + "supportsMockNumbers": True, + "supportsOrganizationRoles": True, + "supportsCredits": True, + "supportsDisposableEmailValidation": True, + "supportsCanonicalEmailValidation": True, + "supportsFreeEmailValidation": True, + "supportsCorporateEmailValidation": True, + "supportsProjectSpecificRoles": True, + "backupsEnabled": True, + "usagePerProject": True, + "supportedAddons": { + "baa": True, + "premiumGeoDB": True, + "premiumGeoDBOrg": True + }, + "backupPolicies": 1.0, + "deploymentSize": 30.0, + "buildSize": 2000.0, + "databasesAllowEncrypt": True, + "group": "pro" + }, + "billingEmail": "billing@org.example", + "billingStartDate": "2020-10-15T06:38:00.000+00:00", + "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialStartDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialDays": 14.0, + "billingAggregationId": "adbc3de4rddfsd", + "billingInvoiceId": "adbc3de4rddfsd", + "paymentMethodId": "adbc3de4rddfsd", + "billingAddressId": "adbc3de4rddfsd", + "backupPaymentMethodId": "adbc3de4rddfsd", + "status": "active", + "remarks": "Pending initial payment", + "agreementBAA": "", + "programManagerName": "", + "programManagerCalendar": "", + "programDiscordChannelName": "", + "programDiscordChannelUrl": "", + "billingPlanDowngrade": "tier-1", + "billingTaxId": "", + "markedForDeletion": True, + "platform": "imagine", + "projects": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.get( + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + "billingBudget": 50.0, + "budgetAlerts": [], + "billingPlan": "tier-1", + "billingPlanId": "tier-1", + "billingPlanDetails": { + "$id": "tier-0", + "name": "Hobby", + "desc": "Hobby plan", + "order": 0.0, + "price": 25, + "trial": 14.0, + "bandwidth": 25.0, + "storage": 25.0, + "imageTransformations": 100.0, + "screenshotsGenerated": 50.0, + "members": 25.0, + "webhooks": 25.0, + "projects": 2.0, + "platforms": 3.0, + "users": 25.0, + "teams": 25.0, + "databases": 25.0, + "databasesReads": 500000.0, + "databasesWrites": 250000.0, + "databasesBatchSize": 100.0, + "buckets": 25.0, + "fileSize": 25.0, + "functions": 25.0, + "sites": 1.0, + "executions": 25.0, + "executionsRetentionCount": 10000.0, + "GBHours": 100.0, + "realtime": 25.0, + "realtimeMessages": 100000.0, + "messages": 1000.0, + "topics": 1.0, + "authPhone": 10.0, + "domains": 5.0, + "activityLogs": 7.0, + "usageLogs": 30.0, + "projectInactivityDays": 7.0, + "alertLimit": 80.0, + "usage": { + "bandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "executions": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "member": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtime": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtimeMessages": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "realtimeBandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "storage": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "users": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "GBHours": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "imageTransformations": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "credits": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + } + }, + "addons": { + "seats": { + "supported": True, + "planIncluded": 1.0, + "limit": 5.0, + "type": "numeric", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + }, + "projects": { + "supported": True, + "planIncluded": 1.0, + "limit": 5.0, + "type": "numeric", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "" + } + }, + "budgetCapEnabled": True, + "customSmtp": True, + "emailBranding": True, + "requiresPaymentMethod": True, + "requiresBillingAddress": True, + "isAvailable": True, + "selfService": True, + "premiumSupport": True, + "budgeting": True, + "supportsMockNumbers": True, + "supportsOrganizationRoles": True, + "supportsCredits": True, + "supportsDisposableEmailValidation": True, + "supportsCanonicalEmailValidation": True, + "supportsFreeEmailValidation": True, + "supportsCorporateEmailValidation": True, + "supportsProjectSpecificRoles": True, + "backupsEnabled": True, + "usagePerProject": True, + "supportedAddons": { + "baa": True, + "premiumGeoDB": True, + "premiumGeoDBOrg": True + }, + "backupPolicies": 1.0, + "deploymentSize": 30.0, + "buildSize": 2000.0, + "databasesAllowEncrypt": True, + "group": "pro" + }, + "billingEmail": "billing@org.example", + "billingStartDate": "2020-10-15T06:38:00.000+00:00", + "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialStartDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialDays": 14.0, + "billingAggregationId": "adbc3de4rddfsd", + "billingInvoiceId": "adbc3de4rddfsd", + "paymentMethodId": "adbc3de4rddfsd", + "billingAddressId": "adbc3de4rddfsd", + "backupPaymentMethodId": "adbc3de4rddfsd", + "status": "active", + "remarks": "Pending initial payment", + "agreementBAA": "", + "programManagerName": "", + "programManagerCalendar": "", + "programDiscordChannelName": "", + "programDiscordChannelUrl": "", + "billingPlanDowngrade": "tier-1", + "billingTaxId": "", + "markedForDeletion": True, + "platform": "imagine", + "projects": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.update( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.delete( + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_list_keys(self, m): data = { @@ -109,6 +571,117 @@ def test_delete_key(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_list_memberships(self, m): + data = { + "total": 5.0, + "memberships": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.list_memberships( + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_membership(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.create_membership( + [], + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_membership(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.get_membership( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_membership(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.update_membership( + '', + [], + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_membership(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.delete_membership( + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_list_projects(self, m): data = { @@ -147,6 +720,7 @@ def test_create_project(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -187,6 +761,7 @@ def test_get_project(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -226,6 +801,7 @@ def test_update_project(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], diff --git a/test/services/test_project.py b/test/services/test_project.py index 9440e29e..c3e87cf3 100644 --- a/test/services/test_project.py +++ b/test/services/test_project.py @@ -37,6 +37,7 @@ def test_get(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -86,6 +87,7 @@ def test_update_auth_method(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -245,6 +247,7 @@ def test_update_labels(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -377,6 +380,7 @@ def test_update_o_auth2_server(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -427,6 +431,22 @@ def test_update_o_auth2_apple(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_update_o_auth2_appwrite(self, m): + data = { + "$id": "github", + "enabled": True, + "clientId": "6a42000000000000b5a0", + "clientSecret": "b86afd000000000000000000000000000000000000000000000000000ced5f93" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.project.update_o_auth2_appwrite( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_update_o_auth2_auth0(self, m): data = { @@ -797,7 +817,8 @@ def test_update_o_auth2_oidc(self, m): "wellKnownURL": "https:\/\/myoauth.com\/.well-known\/openid-configuration", "authorizationURL": "https:\/\/myoauth.com\/oauth2\/authorize", "tokenURL": "https:\/\/myoauth.com\/oauth2\/token", - "userInfoURL": "https:\/\/myoauth.com\/oauth2\/userinfo" + "userInfoURL": "https:\/\/myoauth.com\/oauth2\/userinfo", + "prompt": [] } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1391,6 +1412,7 @@ def test_update_deny_aliased_email_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1430,6 +1452,7 @@ def test_update_deny_corporate_email_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1469,6 +1492,7 @@ def test_update_deny_disposable_email_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1508,6 +1532,7 @@ def test_update_deny_free_email_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1547,6 +1572,7 @@ def test_update_membership_privacy_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1585,6 +1611,7 @@ def test_update_password_dictionary_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1624,6 +1651,7 @@ def test_update_password_history_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1663,6 +1691,7 @@ def test_update_password_personal_data_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1720,6 +1749,7 @@ def test_update_session_alert_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1759,6 +1789,7 @@ def test_update_session_duration_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1798,6 +1829,7 @@ def test_update_session_invalidation_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1837,6 +1869,7 @@ def test_update_session_limit_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1876,6 +1909,7 @@ def test_update_user_limit_policy(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1930,6 +1964,7 @@ def test_update_protocol(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -1970,6 +2005,7 @@ def test_update_service(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], @@ -2010,6 +2046,7 @@ def test_update_smtp(self, m): "pingedAt": "2020-10-15T06:38:00.000+00:00", "labels": [], "status": "active", + "onboarding": {}, "authMethods": [], "services": [], "protocols": [], diff --git a/test/services/test_usage.py b/test/services/test_usage.py deleted file mode 100644 index d54ff32f..00000000 --- a/test/services/test_usage.py +++ /dev/null @@ -1,45 +0,0 @@ -import json -import requests_mock -import unittest - -from appwrite.client import Client -from appwrite.input_file import InputFile -from appwrite.models import * -from appwrite.services.usage import Usage - -class UsageServiceTest(unittest.TestCase): - - def setUp(self): - self.client = Client() - self.usage = Usage(self.client) - - @requests_mock.Mocker() - def test_list_events(self, m): - data = { - "interval": "1d", - "metrics": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.usage.list_events( - [], - ) - - self.assertEqual(response.to_dict(), data) - - @requests_mock.Mocker() - def test_list_gauges(self, m): - data = { - "interval": "1d", - "metrics": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.usage.list_gauges( - [], - ) - - self.assertEqual(response.to_dict(), data) - From 0f3c9d2a792f2066c689d4581b0965139b39b188 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Mon, 13 Jul 2026 12:11:04 +0530 Subject: [PATCH 02/10] chore: update Python SDK to 22.0.0 --- appwrite/client.py | 2 +- appwrite/services/backups.py | 15 +- appwrite/services/databases.py | 207 ++++++++---- appwrite/services/functions.py | 24 +- appwrite/services/messaging.py | 216 ++++++++---- appwrite/services/oauth2.py | 3 +- appwrite/services/organization.py | 6 +- appwrite/services/project.py | 525 ++++++++++++++++++++---------- appwrite/services/sites.py | 18 +- appwrite/services/storage.py | 9 +- appwrite/services/tables_db.py | 210 ++++++++---- appwrite/services/tokens.py | 6 +- appwrite/services/users.py | 6 +- appwrite/services/webhooks.py | 6 +- 14 files changed, 835 insertions(+), 418 deletions(-) diff --git a/appwrite/client.py b/appwrite/client.py index 83f61a8f..0fc438b7 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -70,7 +70,7 @@ def set_jwt(self, value): def set_bearer(self, value): """The OAuth access token to authenticate with""" - self._global_headers['authorization'] = value + self._global_headers['authorization'] = 'Bearer ' + value self._config['bearer'] = value return self diff --git a/appwrite/services/backups.py b/appwrite/services/backups.py index fda14881..5aac7329 100644 --- a/appwrite/services/backups.py +++ b/appwrite/services/backups.py @@ -86,7 +86,8 @@ def create_archive( api_params['services'] = self._normalize_value(services) - api_params['resourceId'] = self._normalize_value(resource_id) + if resource_id is not None: + api_params['resourceId'] = self._normalize_value(resource_id) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -273,7 +274,8 @@ def create_policy( if name is not None: api_params['name'] = self._normalize_value(name) api_params['services'] = self._normalize_value(services) - api_params['resourceId'] = self._normalize_value(resource_id) + if resource_id is not None: + api_params['resourceId'] = self._normalize_value(resource_id) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) api_params['retention'] = self._normalize_value(retention) @@ -369,11 +371,14 @@ def update_policy( api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) - api_params['name'] = self._normalize_value(name) - api_params['retention'] = self._normalize_value(retention) + if name is not None: + api_params['name'] = self._normalize_value(name) + if retention is not None: + api_params['retention'] = self._normalize_value(retention) if schedule is not None: api_params['schedule'] = self._normalize_value(schedule) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/databases.py b/appwrite/services/databases.py index fdc30428..51831aec 100644 --- a/appwrite/services/databases.py +++ b/appwrite/services/databases.py @@ -672,7 +672,8 @@ def create_collection( api_params['collectionId'] = self._normalize_value(collection_id) api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if document_security is not None: api_params['documentSecurity'] = self._normalize_value(document_security) if enabled is not None: @@ -797,7 +798,8 @@ def update_collection( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if document_security is not None: api_params['documentSecurity'] = self._normalize_value(document_security) if enabled is not None: @@ -989,9 +991,12 @@ def create_big_int_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1071,10 +1076,13 @@ def update_big_int_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1146,7 +1154,8 @@ def create_boolean_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1220,7 +1229,8 @@ def update_boolean_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1291,7 +1301,8 @@ def create_datetime_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1365,7 +1376,8 @@ def update_datetime_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1437,7 +1449,8 @@ def create_email_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1512,7 +1525,8 @@ def update_email_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1591,7 +1605,8 @@ def create_enum_attribute( api_params['key'] = self._normalize_value(key) api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1673,7 +1688,8 @@ def update_enum_attribute( api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1751,9 +1767,12 @@ def create_float_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1833,10 +1852,13 @@ def update_float_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1914,9 +1936,12 @@ def create_integer_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1996,10 +2021,13 @@ def update_integer_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2071,7 +2099,8 @@ def create_ip_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -2146,7 +2175,8 @@ def update_ip_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2214,7 +2244,8 @@ def create_line_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2285,8 +2316,10 @@ def update_line_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2361,7 +2394,8 @@ def create_longtext_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -2438,7 +2472,8 @@ def update_longtext_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2513,7 +2548,8 @@ def create_mediumtext_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -2590,7 +2626,8 @@ def update_mediumtext_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2658,7 +2695,8 @@ def create_point_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2729,8 +2767,10 @@ def update_point_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2798,7 +2838,8 @@ def create_polygon_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2869,8 +2910,10 @@ def update_polygon_attribute( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2950,8 +2993,10 @@ def create_relationship_attribute( api_params['type'] = self._normalize_value(type) if two_way is not None: api_params['twoWay'] = self._normalize_value(two_way) - api_params['key'] = self._normalize_value(key) - api_params['twoWayKey'] = self._normalize_value(two_way_key) + if key is not None: + api_params['key'] = self._normalize_value(key) + if two_way_key is not None: + api_params['twoWayKey'] = self._normalize_value(two_way_key) if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) @@ -3020,7 +3065,8 @@ def update_relationship_attribute( if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3102,7 +3148,8 @@ def create_string_attribute( api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -3182,8 +3229,10 @@ def update_string_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['size'] = self._normalize_value(size) - api_params['newKey'] = self._normalize_value(new_key) + if size is not None: + api_params['size'] = self._normalize_value(size) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3258,7 +3307,8 @@ def create_text_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -3335,7 +3385,8 @@ def update_text_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3407,7 +3458,8 @@ def create_url_attribute( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -3482,7 +3534,8 @@ def update_url_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3564,7 +3617,8 @@ def create_varchar_attribute( api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -3644,8 +3698,10 @@ def update_varchar_attribute( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['size'] = self._normalize_value(size) - api_params['newKey'] = self._normalize_value(new_key) + if size is not None: + api_params['size'] = self._normalize_value(size) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3937,8 +3993,10 @@ def create_document( api_params['documentId'] = self._normalize_value(document_id) api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4003,7 +4061,8 @@ def create_documents( api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_params['documents'] = self._normalize_value(documents) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4069,7 +4128,8 @@ def upsert_documents( api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_params['documents'] = self._normalize_value(documents) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4137,7 +4197,8 @@ def update_documents( api_params['data'] = self._normalize_value(data) if queries is not None: api_params['queries'] = self._normalize_value(queries) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4344,8 +4405,10 @@ def upsert_document( if data is not None: api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4418,8 +4481,10 @@ def update_document( if data is not None: api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4560,8 +4625,10 @@ def decrement_document_attribute( if value is not None: api_params['value'] = self._normalize_value(value) - api_params['min'] = self._normalize_value(min) - api_params['transactionId'] = self._normalize_value(transaction_id) + if min is not None: + api_params['min'] = self._normalize_value(min) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4641,8 +4708,10 @@ def increment_document_attribute( if value is not None: api_params['value'] = self._normalize_value(value) - api_params['max'] = self._normalize_value(max) - api_params['transactionId'] = self._normalize_value(transaction_id) + if max is not None: + api_params['max'] = self._normalize_value(max) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/functions.py b/appwrite/services/functions.py index 18709fb2..4b0f552f 100644 --- a/appwrite/services/functions.py +++ b/appwrite/services/functions.py @@ -445,16 +445,20 @@ def update( api_params['scopes'] = self._normalize_value(scopes) if installation_id is not None: api_params['installationId'] = self._normalize_value(installation_id) - api_params['providerRepositoryId'] = self._normalize_value(provider_repository_id) + if provider_repository_id is not None: + api_params['providerRepositoryId'] = self._normalize_value(provider_repository_id) if provider_branch is not None: api_params['providerBranch'] = self._normalize_value(provider_branch) if provider_silent_mode is not None: api_params['providerSilentMode'] = self._normalize_value(provider_silent_mode) if provider_root_directory is not None: api_params['providerRootDirectory'] = self._normalize_value(provider_root_directory) - api_params['providerBranches'] = self._normalize_value(provider_branches) - api_params['providerPaths'] = self._normalize_value(provider_paths) - api_params['buildSpecification'] = self._normalize_value(build_specification) + if provider_branches is not None: + api_params['providerBranches'] = self._normalize_value(provider_branches) + if provider_paths is not None: + api_params['providerPaths'] = self._normalize_value(provider_paths) + if build_specification is not None: + api_params['buildSpecification'] = self._normalize_value(build_specification) if runtime_specification is not None: api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: @@ -1182,7 +1186,8 @@ def create_execution( api_params['method'] = self._normalize_value(method) if headers is not None: api_params['headers'] = self._normalize_value(headers) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1492,9 +1497,12 @@ def update_variable( api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - api_params['key'] = self._normalize_value(key) - api_params['value'] = self._normalize_value(value) - api_params['secret'] = self._normalize_value(secret) + if key is not None: + api_params['key'] = self._normalize_value(key) + if value is not None: + api_params['value'] = self._normalize_value(value) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/messaging.py b/appwrite/services/messaging.py index 3abb1004..2ebe2bd6 100644 --- a/appwrite/services/messaging.py +++ b/appwrite/services/messaging.py @@ -154,7 +154,8 @@ def create_email( api_params['draft'] = self._normalize_value(draft) if html is not None: api_params['html'] = self._normalize_value(html) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -229,17 +230,28 @@ def update_email( api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - api_params['topics'] = self._normalize_value(topics) - api_params['users'] = self._normalize_value(users) - api_params['targets'] = self._normalize_value(targets) - api_params['subject'] = self._normalize_value(subject) - api_params['content'] = self._normalize_value(content) - api_params['draft'] = self._normalize_value(draft) - api_params['html'] = self._normalize_value(html) - api_params['cc'] = self._normalize_value(cc) - api_params['bcc'] = self._normalize_value(bcc) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) - api_params['attachments'] = self._normalize_value(attachments) + if topics is not None: + api_params['topics'] = self._normalize_value(topics) + if users is not None: + api_params['users'] = self._normalize_value(users) + if targets is not None: + api_params['targets'] = self._normalize_value(targets) + if subject is not None: + api_params['subject'] = self._normalize_value(subject) + if content is not None: + api_params['content'] = self._normalize_value(content) + if draft is not None: + api_params['draft'] = self._normalize_value(draft) + if html is not None: + api_params['html'] = self._normalize_value(html) + if cc is not None: + api_params['cc'] = self._normalize_value(cc) + if bcc is not None: + api_params['bcc'] = self._normalize_value(bcc) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if attachments is not None: + api_params['attachments'] = self._normalize_value(attachments) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -344,7 +356,8 @@ def create_push( api_params['users'] = self._normalize_value(users) if targets is not None: api_params['targets'] = self._normalize_value(targets) - api_params['data'] = self._normalize_value(data) + if data is not None: + api_params['data'] = self._normalize_value(data) if action is not None: api_params['action'] = self._normalize_value(action) if image is not None: @@ -361,7 +374,8 @@ def create_push( api_params['badge'] = self._normalize_value(badge) if draft is not None: api_params['draft'] = self._normalize_value(draft) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) if content_available is not None: api_params['contentAvailable'] = self._normalize_value(content_available) if critical is not None: @@ -463,24 +477,42 @@ def update_push( api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - api_params['topics'] = self._normalize_value(topics) - api_params['users'] = self._normalize_value(users) - api_params['targets'] = self._normalize_value(targets) - api_params['title'] = self._normalize_value(title) - api_params['body'] = self._normalize_value(body) - api_params['data'] = self._normalize_value(data) - api_params['action'] = self._normalize_value(action) - api_params['image'] = self._normalize_value(image) - api_params['icon'] = self._normalize_value(icon) - api_params['sound'] = self._normalize_value(sound) - api_params['color'] = self._normalize_value(color) - api_params['tag'] = self._normalize_value(tag) - api_params['badge'] = self._normalize_value(badge) - api_params['draft'] = self._normalize_value(draft) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) - api_params['contentAvailable'] = self._normalize_value(content_available) - api_params['critical'] = self._normalize_value(critical) - api_params['priority'] = self._normalize_value(priority) + if topics is not None: + api_params['topics'] = self._normalize_value(topics) + if users is not None: + api_params['users'] = self._normalize_value(users) + if targets is not None: + api_params['targets'] = self._normalize_value(targets) + if title is not None: + api_params['title'] = self._normalize_value(title) + if body is not None: + api_params['body'] = self._normalize_value(body) + if data is not None: + api_params['data'] = self._normalize_value(data) + if action is not None: + api_params['action'] = self._normalize_value(action) + if image is not None: + api_params['image'] = self._normalize_value(image) + if icon is not None: + api_params['icon'] = self._normalize_value(icon) + if sound is not None: + api_params['sound'] = self._normalize_value(sound) + if color is not None: + api_params['color'] = self._normalize_value(color) + if tag is not None: + api_params['tag'] = self._normalize_value(tag) + if badge is not None: + api_params['badge'] = self._normalize_value(badge) + if draft is not None: + api_params['draft'] = self._normalize_value(draft) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if content_available is not None: + api_params['contentAvailable'] = self._normalize_value(content_available) + if critical is not None: + api_params['critical'] = self._normalize_value(critical) + if priority is not None: + api_params['priority'] = self._normalize_value(priority) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -551,7 +583,8 @@ def create_sms( api_params['targets'] = self._normalize_value(targets) if draft is not None: api_params['draft'] = self._normalize_value(draft) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -611,12 +644,18 @@ def update_sms( api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - api_params['topics'] = self._normalize_value(topics) - api_params['users'] = self._normalize_value(users) - api_params['targets'] = self._normalize_value(targets) - api_params['content'] = self._normalize_value(content) - api_params['draft'] = self._normalize_value(draft) - api_params['scheduledAt'] = self._normalize_value(scheduled_at) + if topics is not None: + api_params['topics'] = self._normalize_value(topics) + if users is not None: + api_params['users'] = self._normalize_value(users) + if targets is not None: + api_params['targets'] = self._normalize_value(targets) + if content is not None: + api_params['content'] = self._normalize_value(content) + if draft is not None: + api_params['draft'] = self._normalize_value(draft) + if scheduled_at is not None: + api_params['scheduledAt'] = self._normalize_value(scheduled_at) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -867,7 +906,8 @@ def create_apns_provider( api_params['bundleId'] = self._normalize_value(bundle_id) if sandbox is not None: api_params['sandbox'] = self._normalize_value(sandbox) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -931,7 +971,8 @@ def update_apns_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if auth_key is not None: api_params['authKey'] = self._normalize_value(auth_key) if auth_key_id is not None: @@ -940,7 +981,8 @@ def update_apns_provider( api_params['teamId'] = self._normalize_value(team_id) if bundle_id is not None: api_params['bundleId'] = self._normalize_value(bundle_id) - api_params['sandbox'] = self._normalize_value(sandbox) + if sandbox is not None: + api_params['sandbox'] = self._normalize_value(sandbox) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -994,8 +1036,10 @@ def create_fcm_provider( api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) - api_params['serviceAccountJSON'] = self._normalize_value(service_account_json) - api_params['enabled'] = self._normalize_value(enabled) + if service_account_json is not None: + api_params['serviceAccountJSON'] = self._normalize_value(service_account_json) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1047,8 +1091,10 @@ def update_fcm_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) - api_params['serviceAccountJSON'] = self._normalize_value(service_account_json) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if service_account_json is not None: + api_params['serviceAccountJSON'] = self._normalize_value(service_account_json) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1124,7 +1170,8 @@ def create_mailgun_provider( api_params['apiKey'] = self._normalize_value(api_key) if domain is not None: api_params['domain'] = self._normalize_value(domain) - api_params['isEuRegion'] = self._normalize_value(is_eu_region) + if is_eu_region is not None: + api_params['isEuRegion'] = self._normalize_value(is_eu_region) if from_name is not None: api_params['fromName'] = self._normalize_value(from_name) if from_email is not None: @@ -1133,7 +1180,8 @@ def create_mailgun_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1207,8 +1255,10 @@ def update_mailgun_provider( api_params['apiKey'] = self._normalize_value(api_key) if domain is not None: api_params['domain'] = self._normalize_value(domain) - api_params['isEuRegion'] = self._normalize_value(is_eu_region) - api_params['enabled'] = self._normalize_value(enabled) + if is_eu_region is not None: + api_params['isEuRegion'] = self._normalize_value(is_eu_region) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if from_name is not None: api_params['fromName'] = self._normalize_value(from_name) if from_email is not None: @@ -1282,7 +1332,8 @@ def create_msg91_provider( api_params['senderId'] = self._normalize_value(sender_id) if auth_key is not None: api_params['authKey'] = self._normalize_value(auth_key) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1340,7 +1391,8 @@ def update_msg91_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if template_id is not None: api_params['templateId'] = self._normalize_value(template_id) if sender_id is not None: @@ -1422,7 +1474,8 @@ def create_resend_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1486,7 +1539,8 @@ def update_resend_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) if from_name is not None: @@ -1572,7 +1626,8 @@ def create_sendgrid_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1636,7 +1691,8 @@ def update_sendgrid_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) if from_name is not None: @@ -1732,7 +1788,8 @@ def create_ses_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1802,7 +1859,8 @@ def update_ses_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if access_key is not None: api_params['accessKey'] = self._normalize_value(access_key) if secret_key is not None: @@ -1924,7 +1982,8 @@ def create_smtp_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2008,14 +2067,16 @@ def update_smtp_provider( api_params['name'] = self._normalize_value(name) if host is not None: api_params['host'] = self._normalize_value(host) - api_params['port'] = self._normalize_value(port) + if port is not None: + api_params['port'] = self._normalize_value(port) if username is not None: api_params['username'] = self._normalize_value(username) if password is not None: api_params['password'] = self._normalize_value(password) if encryption is not None: api_params['encryption'] = self._normalize_value(encryption) - api_params['autoTLS'] = self._normalize_value(auto_tls) + if auto_tls is not None: + api_params['autoTLS'] = self._normalize_value(auto_tls) if mailer is not None: api_params['mailer'] = self._normalize_value(mailer) if from_name is not None: @@ -2026,7 +2087,8 @@ def update_smtp_provider( api_params['replyToName'] = self._normalize_value(reply_to_name) if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2092,7 +2154,8 @@ def create_telesign_provider( api_params['customerId'] = self._normalize_value(customer_id) if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2150,7 +2213,8 @@ def update_telesign_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if customer_id is not None: api_params['customerId'] = self._normalize_value(customer_id) if api_key is not None: @@ -2222,7 +2286,8 @@ def create_textmagic_provider( api_params['username'] = self._normalize_value(username) if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2280,7 +2345,8 @@ def update_textmagic_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if username is not None: api_params['username'] = self._normalize_value(username) if api_key is not None: @@ -2352,7 +2418,8 @@ def create_twilio_provider( api_params['accountSid'] = self._normalize_value(account_sid) if auth_token is not None: api_params['authToken'] = self._normalize_value(auth_token) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2410,7 +2477,8 @@ def update_twilio_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if account_sid is not None: api_params['accountSid'] = self._normalize_value(account_sid) if auth_token is not None: @@ -2482,7 +2550,8 @@ def create_vonage_provider( api_params['apiKey'] = self._normalize_value(api_key) if api_secret is not None: api_params['apiSecret'] = self._normalize_value(api_secret) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2540,7 +2609,8 @@ def update_vonage_provider( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['enabled'] = self._normalize_value(enabled) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) if api_secret is not None: @@ -2812,8 +2882,10 @@ def update_topic( api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - api_params['name'] = self._normalize_value(name) - api_params['subscribe'] = self._normalize_value(subscribe) + if name is not None: + api_params['name'] = self._normalize_value(name) + if subscribe is not None: + api_params['subscribe'] = self._normalize_value(subscribe) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/oauth2.py b/appwrite/services/oauth2.py index 272fbc73..21612207 100644 --- a/appwrite/services/oauth2.py +++ b/appwrite/services/oauth2.py @@ -441,7 +441,8 @@ def create_par( api_params['code_challenge_method'] = self._normalize_value(code_challenge_method) if prompt is not None: api_params['prompt'] = self._normalize_value(prompt) - api_params['max_age'] = self._normalize_value(max_age) + if max_age is not None: + api_params['max_age'] = self._normalize_value(max_age) if authorization_details is not None: api_params['authorization_details'] = self._normalize_value(authorization_details) if resource is not None: diff --git a/appwrite/services/organization.py b/appwrite/services/organization.py index eaf0ca88..e3f11e50 100644 --- a/appwrite/services/organization.py +++ b/appwrite/services/organization.py @@ -216,7 +216,8 @@ def create_key( api_params['keyId'] = self._normalize_value(key_id) api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -313,7 +314,8 @@ def update_key( api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/project.py b/appwrite/services/project.py index c9d5c9d4..573abdae 100644 --- a/appwrite/services/project.py +++ b/appwrite/services/project.py @@ -286,7 +286,8 @@ def create_key( api_params['keyId'] = self._normalize_value(key_id) api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -432,7 +433,8 @@ def update_key( api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -855,17 +857,24 @@ def update_o_auth2_server( api_params['scopes'] = self._normalize_value(scopes) if authorization_details_types is not None: api_params['authorizationDetailsTypes'] = self._normalize_value(authorization_details_types) - api_params['accessTokenDuration'] = self._normalize_value(access_token_duration) - api_params['refreshTokenDuration'] = self._normalize_value(refresh_token_duration) - api_params['publicAccessTokenDuration'] = self._normalize_value(public_access_token_duration) - api_params['publicRefreshTokenDuration'] = self._normalize_value(public_refresh_token_duration) - api_params['confidentialPkce'] = self._normalize_value(confidential_pkce) + if access_token_duration is not None: + api_params['accessTokenDuration'] = self._normalize_value(access_token_duration) + if refresh_token_duration is not None: + api_params['refreshTokenDuration'] = self._normalize_value(refresh_token_duration) + if public_access_token_duration is not None: + api_params['publicAccessTokenDuration'] = self._normalize_value(public_access_token_duration) + if public_refresh_token_duration is not None: + api_params['publicRefreshTokenDuration'] = self._normalize_value(public_refresh_token_duration) + if confidential_pkce is not None: + api_params['confidentialPkce'] = self._normalize_value(confidential_pkce) if verification_url is not None: api_params['verificationUrl'] = self._normalize_value(verification_url) - api_params['userCodeLength'] = self._normalize_value(user_code_length) + if user_code_length is not None: + api_params['userCodeLength'] = self._normalize_value(user_code_length) if user_code_format is not None: api_params['userCodeFormat'] = self._normalize_value(user_code_format) - api_params['deviceCodeDuration'] = self._normalize_value(device_code_duration) + if device_code_duration is not None: + api_params['deviceCodeDuration'] = self._normalize_value(device_code_duration) if default_scopes is not None: api_params['defaultScopes'] = self._normalize_value(default_scopes) @@ -910,9 +919,12 @@ def update_o_auth2_amazon( api_path = '/project/oauth2/amazon' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -961,11 +973,16 @@ def update_o_auth2_apple( api_path = '/project/oauth2/apple' api_params = {} - api_params['serviceId'] = self._normalize_value(service_id) - api_params['keyId'] = self._normalize_value(key_id) - api_params['teamId'] = self._normalize_value(team_id) - api_params['p8File'] = self._normalize_value(p8_file) - api_params['enabled'] = self._normalize_value(enabled) + if service_id is not None: + api_params['serviceId'] = self._normalize_value(service_id) + if key_id is not None: + api_params['keyId'] = self._normalize_value(key_id) + if team_id is not None: + api_params['teamId'] = self._normalize_value(team_id) + if p8_file is not None: + api_params['p8File'] = self._normalize_value(p8_file) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1008,9 +1025,12 @@ def update_o_auth2_appwrite( api_path = '/project/oauth2/appwrite' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1056,10 +1076,14 @@ def update_o_auth2_auth0( api_path = '/project/oauth2/auth0' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['endpoint'] = self._normalize_value(endpoint) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1105,10 +1129,14 @@ def update_o_auth2_authentik( api_path = '/project/oauth2/authentik' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['endpoint'] = self._normalize_value(endpoint) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1151,9 +1179,12 @@ def update_o_auth2_autodesk( api_path = '/project/oauth2/autodesk' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1196,9 +1227,12 @@ def update_o_auth2_bitbucket( api_path = '/project/oauth2/bitbucket' api_params = {} - api_params['key'] = self._normalize_value(key) - api_params['secret'] = self._normalize_value(secret) - api_params['enabled'] = self._normalize_value(enabled) + if key is not None: + api_params['key'] = self._normalize_value(key) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1241,9 +1275,12 @@ def update_o_auth2_bitly( api_path = '/project/oauth2/bitly' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1286,9 +1323,12 @@ def update_o_auth2_box( api_path = '/project/oauth2/box' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1331,9 +1371,12 @@ def update_o_auth2_dailymotion( api_path = '/project/oauth2/dailymotion' api_params = {} - api_params['apiKey'] = self._normalize_value(api_key) - api_params['apiSecret'] = self._normalize_value(api_secret) - api_params['enabled'] = self._normalize_value(enabled) + if api_key is not None: + api_params['apiKey'] = self._normalize_value(api_key) + if api_secret is not None: + api_params['apiSecret'] = self._normalize_value(api_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1376,9 +1419,12 @@ def update_o_auth2_discord( api_path = '/project/oauth2/discord' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1421,9 +1467,12 @@ def update_o_auth2_disqus( api_path = '/project/oauth2/disqus' api_params = {} - api_params['publicKey'] = self._normalize_value(public_key) - api_params['secretKey'] = self._normalize_value(secret_key) - api_params['enabled'] = self._normalize_value(enabled) + if public_key is not None: + api_params['publicKey'] = self._normalize_value(public_key) + if secret_key is not None: + api_params['secretKey'] = self._normalize_value(secret_key) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1466,9 +1515,12 @@ def update_o_auth2_dropbox( api_path = '/project/oauth2/dropbox' api_params = {} - api_params['appKey'] = self._normalize_value(app_key) - api_params['appSecret'] = self._normalize_value(app_secret) - api_params['enabled'] = self._normalize_value(enabled) + if app_key is not None: + api_params['appKey'] = self._normalize_value(app_key) + if app_secret is not None: + api_params['appSecret'] = self._normalize_value(app_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1511,9 +1563,12 @@ def update_o_auth2_etsy( api_path = '/project/oauth2/etsy' api_params = {} - api_params['keyString'] = self._normalize_value(key_string) - api_params['sharedSecret'] = self._normalize_value(shared_secret) - api_params['enabled'] = self._normalize_value(enabled) + if key_string is not None: + api_params['keyString'] = self._normalize_value(key_string) + if shared_secret is not None: + api_params['sharedSecret'] = self._normalize_value(shared_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1556,9 +1611,12 @@ def update_o_auth2_facebook( api_path = '/project/oauth2/facebook' api_params = {} - api_params['appId'] = self._normalize_value(app_id) - api_params['appSecret'] = self._normalize_value(app_secret) - api_params['enabled'] = self._normalize_value(enabled) + if app_id is not None: + api_params['appId'] = self._normalize_value(app_id) + if app_secret is not None: + api_params['appSecret'] = self._normalize_value(app_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1601,9 +1659,12 @@ def update_o_auth2_figma( api_path = '/project/oauth2/figma' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1649,10 +1710,14 @@ def update_o_auth2_fusion_auth( api_path = '/project/oauth2/fusionauth' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['endpoint'] = self._normalize_value(endpoint) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1695,9 +1760,12 @@ def update_o_auth2_git_hub( api_path = '/project/oauth2/github' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1743,10 +1811,14 @@ def update_o_auth2_gitlab( api_path = '/project/oauth2/gitlab' api_params = {} - api_params['applicationId'] = self._normalize_value(application_id) - api_params['secret'] = self._normalize_value(secret) - api_params['endpoint'] = self._normalize_value(endpoint) - api_params['enabled'] = self._normalize_value(enabled) + if application_id is not None: + api_params['applicationId'] = self._normalize_value(application_id) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1792,10 +1864,14 @@ def update_o_auth2_google( api_path = '/project/oauth2/google' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['prompt'] = self._normalize_value(prompt) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if prompt is not None: + api_params['prompt'] = self._normalize_value(prompt) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1844,11 +1920,16 @@ def update_o_auth2_keycloak( api_path = '/project/oauth2/keycloak' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['endpoint'] = self._normalize_value(endpoint) - api_params['realmName'] = self._normalize_value(realm_name) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + if realm_name is not None: + api_params['realmName'] = self._normalize_value(realm_name) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1891,9 +1972,12 @@ def update_o_auth2_kick( api_path = '/project/oauth2/kick' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1936,9 +2020,12 @@ def update_o_auth2_linkedin( api_path = '/project/oauth2/linkedin' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['primaryClientSecret'] = self._normalize_value(primary_client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if primary_client_secret is not None: + api_params['primaryClientSecret'] = self._normalize_value(primary_client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1984,10 +2071,14 @@ def update_o_auth2_microsoft( api_path = '/project/oauth2/microsoft' api_params = {} - api_params['applicationId'] = self._normalize_value(application_id) - api_params['applicationSecret'] = self._normalize_value(application_secret) - api_params['tenant'] = self._normalize_value(tenant) - api_params['enabled'] = self._normalize_value(enabled) + if application_id is not None: + api_params['applicationId'] = self._normalize_value(application_id) + if application_secret is not None: + api_params['applicationSecret'] = self._normalize_value(application_secret) + if tenant is not None: + api_params['tenant'] = self._normalize_value(tenant) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2030,9 +2121,12 @@ def update_o_auth2_notion( api_path = '/project/oauth2/notion' api_params = {} - api_params['oauthClientId'] = self._normalize_value(oauth_client_id) - api_params['oauthClientSecret'] = self._normalize_value(oauth_client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if oauth_client_id is not None: + api_params['oauthClientId'] = self._normalize_value(oauth_client_id) + if oauth_client_secret is not None: + api_params['oauthClientSecret'] = self._normalize_value(oauth_client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2093,15 +2187,24 @@ def update_o_auth2_oidc( api_path = '/project/oauth2/oidc' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['wellKnownURL'] = self._normalize_value(well_known_url) - api_params['authorizationURL'] = self._normalize_value(authorization_url) - api_params['tokenURL'] = self._normalize_value(token_url) - api_params['userInfoURL'] = self._normalize_value(user_info_url) - api_params['prompt'] = self._normalize_value(prompt) - api_params['maxAge'] = self._normalize_value(max_age) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if well_known_url is not None: + api_params['wellKnownURL'] = self._normalize_value(well_known_url) + if authorization_url is not None: + api_params['authorizationURL'] = self._normalize_value(authorization_url) + if token_url is not None: + api_params['tokenURL'] = self._normalize_value(token_url) + if user_info_url is not None: + api_params['userInfoURL'] = self._normalize_value(user_info_url) + if prompt is not None: + api_params['prompt'] = self._normalize_value(prompt) + if max_age is not None: + api_params['maxAge'] = self._normalize_value(max_age) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2150,11 +2253,16 @@ def update_o_auth2_okta( api_path = '/project/oauth2/okta' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['domain'] = self._normalize_value(domain) - api_params['authorizationServerId'] = self._normalize_value(authorization_server_id) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if domain is not None: + api_params['domain'] = self._normalize_value(domain) + if authorization_server_id is not None: + api_params['authorizationServerId'] = self._normalize_value(authorization_server_id) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2197,9 +2305,12 @@ def update_o_auth2_paypal( api_path = '/project/oauth2/paypal' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['secretKey'] = self._normalize_value(secret_key) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if secret_key is not None: + api_params['secretKey'] = self._normalize_value(secret_key) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2242,9 +2353,12 @@ def update_o_auth2_paypal_sandbox( api_path = '/project/oauth2/paypalSandbox' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['secretKey'] = self._normalize_value(secret_key) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if secret_key is not None: + api_params['secretKey'] = self._normalize_value(secret_key) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2287,9 +2401,12 @@ def update_o_auth2_podio( api_path = '/project/oauth2/podio' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2332,9 +2449,12 @@ def update_o_auth2_salesforce( api_path = '/project/oauth2/salesforce' api_params = {} - api_params['customerKey'] = self._normalize_value(customer_key) - api_params['customerSecret'] = self._normalize_value(customer_secret) - api_params['enabled'] = self._normalize_value(enabled) + if customer_key is not None: + api_params['customerKey'] = self._normalize_value(customer_key) + if customer_secret is not None: + api_params['customerSecret'] = self._normalize_value(customer_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2377,9 +2497,12 @@ def update_o_auth2_slack( api_path = '/project/oauth2/slack' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2422,9 +2545,12 @@ def update_o_auth2_spotify( api_path = '/project/oauth2/spotify' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2467,9 +2593,12 @@ def update_o_auth2_stripe( api_path = '/project/oauth2/stripe' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['apiSecretKey'] = self._normalize_value(api_secret_key) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if api_secret_key is not None: + api_params['apiSecretKey'] = self._normalize_value(api_secret_key) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2512,9 +2641,12 @@ def update_o_auth2_tradeshift( api_path = '/project/oauth2/tradeshift' api_params = {} - api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) - api_params['oauth2ClientSecret'] = self._normalize_value(oauth2_client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if oauth2_client_id is not None: + api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) + if oauth2_client_secret is not None: + api_params['oauth2ClientSecret'] = self._normalize_value(oauth2_client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2557,9 +2689,12 @@ def update_o_auth2_tradeshift_sandbox( api_path = '/project/oauth2/tradeshiftBox' api_params = {} - api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) - api_params['oauth2ClientSecret'] = self._normalize_value(oauth2_client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if oauth2_client_id is not None: + api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) + if oauth2_client_secret is not None: + api_params['oauth2ClientSecret'] = self._normalize_value(oauth2_client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2602,9 +2737,12 @@ def update_o_auth2_twitch( api_path = '/project/oauth2/twitch' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2647,9 +2785,12 @@ def update_o_auth2_word_press( api_path = '/project/oauth2/wordpress' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2692,9 +2833,12 @@ def update_o_auth2_x( api_path = '/project/oauth2/x' api_params = {} - api_params['customerKey'] = self._normalize_value(customer_key) - api_params['secretKey'] = self._normalize_value(secret_key) - api_params['enabled'] = self._normalize_value(enabled) + if customer_key is not None: + api_params['customerKey'] = self._normalize_value(customer_key) + if secret_key is not None: + api_params['secretKey'] = self._normalize_value(secret_key) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2737,9 +2881,12 @@ def update_o_auth2_yahoo( api_path = '/project/oauth2/yahoo' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2782,9 +2929,12 @@ def update_o_auth2_yandex( api_path = '/project/oauth2/yandex' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2827,9 +2977,12 @@ def update_o_auth2_zoho( api_path = '/project/oauth2/zoho' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2872,9 +3025,12 @@ def update_o_auth2_zoom( api_path = '/project/oauth2/zoom' api_params = {} - api_params['clientId'] = self._normalize_value(client_id) - api_params['clientSecret'] = self._normalize_value(client_secret) - api_params['enabled'] = self._normalize_value(enabled) + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4589,16 +4745,26 @@ def update_smtp( api_path = '/project/smtp' api_params = {} - api_params['host'] = self._normalize_value(host) - api_params['port'] = self._normalize_value(port) - api_params['username'] = self._normalize_value(username) - api_params['password'] = self._normalize_value(password) - api_params['senderEmail'] = self._normalize_value(sender_email) - api_params['senderName'] = self._normalize_value(sender_name) - api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['replyToName'] = self._normalize_value(reply_to_name) - api_params['secure'] = self._normalize_value(secure) - api_params['enabled'] = self._normalize_value(enabled) + if host is not None: + api_params['host'] = self._normalize_value(host) + if port is not None: + api_params['port'] = self._normalize_value(port) + if username is not None: + api_params['username'] = self._normalize_value(username) + if password is not None: + api_params['password'] = self._normalize_value(password) + if sender_email is not None: + api_params['senderEmail'] = self._normalize_value(sender_email) + if sender_name is not None: + api_params['senderName'] = self._normalize_value(sender_name) + if reply_to_email is not None: + api_params['replyToEmail'] = self._normalize_value(reply_to_email) + if reply_to_name is not None: + api_params['replyToName'] = self._normalize_value(reply_to_name) + if secure is not None: + api_params['secure'] = self._normalize_value(secure) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4743,12 +4909,18 @@ def update_email_template( api_params['templateId'] = self._normalize_value(template_id) if locale is not None: api_params['locale'] = self._normalize_value(locale) - api_params['subject'] = self._normalize_value(subject) - api_params['message'] = self._normalize_value(message) - api_params['senderName'] = self._normalize_value(sender_name) - api_params['senderEmail'] = self._normalize_value(sender_email) - api_params['replyToEmail'] = self._normalize_value(reply_to_email) - api_params['replyToName'] = self._normalize_value(reply_to_name) + if subject is not None: + api_params['subject'] = self._normalize_value(subject) + if message is not None: + api_params['message'] = self._normalize_value(message) + if sender_name is not None: + api_params['senderName'] = self._normalize_value(sender_name) + if sender_email is not None: + api_params['senderEmail'] = self._normalize_value(sender_email) + if reply_to_email is not None: + api_params['replyToEmail'] = self._normalize_value(reply_to_email) + if reply_to_name is not None: + api_params['replyToName'] = self._normalize_value(reply_to_name) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4982,9 +5154,12 @@ def update_variable( api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - api_params['key'] = self._normalize_value(key) - api_params['value'] = self._normalize_value(value) - api_params['secret'] = self._normalize_value(secret) + if key is not None: + api_params['key'] = self._normalize_value(key) + if value is not None: + api_params['value'] = self._normalize_value(value) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/sites.py b/appwrite/services/sites.py index 4daf161f..611dcb02 100644 --- a/appwrite/services/sites.py +++ b/appwrite/services/sites.py @@ -467,9 +467,12 @@ def update( api_params['providerSilentMode'] = self._normalize_value(provider_silent_mode) if provider_root_directory is not None: api_params['providerRootDirectory'] = self._normalize_value(provider_root_directory) - api_params['providerBranches'] = self._normalize_value(provider_branches) - api_params['providerPaths'] = self._normalize_value(provider_paths) - api_params['buildSpecification'] = self._normalize_value(build_specification) + if provider_branches is not None: + api_params['providerBranches'] = self._normalize_value(provider_branches) + if provider_paths is not None: + api_params['providerPaths'] = self._normalize_value(provider_paths) + if build_specification is not None: + api_params['buildSpecification'] = self._normalize_value(build_specification) if runtime_specification is not None: api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: @@ -1428,9 +1431,12 @@ def update_variable( api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - api_params['key'] = self._normalize_value(key) - api_params['value'] = self._normalize_value(value) - api_params['secret'] = self._normalize_value(secret) + if key is not None: + api_params['key'] = self._normalize_value(key) + if value is not None: + api_params['value'] = self._normalize_value(value) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/storage.py b/appwrite/services/storage.py index 7d1a1eaf..a450e58b 100644 --- a/appwrite/services/storage.py +++ b/appwrite/services/storage.py @@ -128,7 +128,8 @@ def create_bucket( api_params['bucketId'] = self._normalize_value(bucket_id) api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if file_security is not None: api_params['fileSecurity'] = self._normalize_value(file_security) if enabled is not None: @@ -258,7 +259,8 @@ def update_bucket( api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if file_security is not None: api_params['fileSecurity'] = self._normalize_value(file_security) if enabled is not None: @@ -544,7 +546,8 @@ def update_file( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/tables_db.py b/appwrite/services/tables_db.py index 9733bc96..806bdc84 100644 --- a/appwrite/services/tables_db.py +++ b/appwrite/services/tables_db.py @@ -638,7 +638,8 @@ def create_table( api_params['tableId'] = self._normalize_value(table_id) api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if row_security is not None: api_params['rowSecurity'] = self._normalize_value(row_security) if enabled is not None: @@ -757,7 +758,8 @@ def update_table( if name is not None: api_params['name'] = self._normalize_value(name) - api_params['permissions'] = self._normalize_value(permissions) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) if row_security is not None: api_params['rowSecurity'] = self._normalize_value(row_security) if enabled is not None: @@ -940,9 +942,12 @@ def create_big_int_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1019,10 +1024,13 @@ def update_big_int_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1091,7 +1099,8 @@ def create_boolean_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1162,7 +1171,8 @@ def update_boolean_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1230,7 +1240,8 @@ def create_datetime_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1301,7 +1312,8 @@ def update_datetime_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1370,7 +1382,8 @@ def create_email_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1442,7 +1455,8 @@ def update_email_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1517,7 +1531,8 @@ def create_enum_column( api_params['key'] = self._normalize_value(key) api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1596,7 +1611,8 @@ def update_enum_column( api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1671,9 +1687,12 @@ def create_float_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1750,10 +1769,13 @@ def update_float_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1828,9 +1850,12 @@ def create_integer_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) - api_params['default'] = self._normalize_value(default) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -1907,10 +1932,13 @@ def update_integer_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['min'] = self._normalize_value(min) - api_params['max'] = self._normalize_value(max) + if min is not None: + api_params['min'] = self._normalize_value(min) + if max is not None: + api_params['max'] = self._normalize_value(max) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -1979,7 +2007,8 @@ def create_ip_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -2051,7 +2080,8 @@ def update_ip_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2116,7 +2146,8 @@ def create_line_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2184,8 +2215,10 @@ def update_line_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2257,7 +2290,8 @@ def create_longtext_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -2331,7 +2365,8 @@ def update_longtext_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2403,7 +2438,8 @@ def create_mediumtext_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -2477,7 +2513,8 @@ def update_mediumtext_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2542,7 +2579,8 @@ def create_point_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2610,8 +2648,10 @@ def update_point_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2676,7 +2716,8 @@ def create_polygon_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2744,8 +2785,10 @@ def update_polygon_column( api_path = api_path.replace('{key}', str(self._normalize_value(key))) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if default is not None: + api_params['default'] = self._normalize_value(default) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -2822,8 +2865,10 @@ def create_relationship_column( api_params['type'] = self._normalize_value(type) if two_way is not None: api_params['twoWay'] = self._normalize_value(two_way) - api_params['key'] = self._normalize_value(key) - api_params['twoWayKey'] = self._normalize_value(two_way_key) + if key is not None: + api_params['key'] = self._normalize_value(key) + if two_way_key is not None: + api_params['twoWayKey'] = self._normalize_value(two_way_key) if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) @@ -2907,7 +2952,8 @@ def create_string_column( api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -2987,8 +3033,10 @@ def update_string_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['size'] = self._normalize_value(size) - api_params['newKey'] = self._normalize_value(new_key) + if size is not None: + api_params['size'] = self._normalize_value(size) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3060,7 +3108,8 @@ def create_text_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -3134,7 +3183,8 @@ def update_text_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3203,7 +3253,8 @@ def create_url_column( api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) @@ -3275,7 +3326,8 @@ def update_url_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['newKey'] = self._normalize_value(new_key) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3354,7 +3406,8 @@ def create_varchar_column( api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) - api_params['default'] = self._normalize_value(default) + if default is not None: + api_params['default'] = self._normalize_value(default) if array is not None: api_params['array'] = self._normalize_value(array) if encrypt is not None: @@ -3431,8 +3484,10 @@ def update_varchar_column( api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) - api_params['size'] = self._normalize_value(size) - api_params['newKey'] = self._normalize_value(new_key) + if size is not None: + api_params['size'] = self._normalize_value(size) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -3632,8 +3687,10 @@ def update_relationship_column( api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['onDelete'] = self._normalize_value(on_delete) - api_params['newKey'] = self._normalize_value(new_key) + if on_delete is not None: + api_params['onDelete'] = self._normalize_value(on_delete) + if new_key is not None: + api_params['newKey'] = self._normalize_value(new_key) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4016,8 +4073,10 @@ def create_row( api_params['rowId'] = self._normalize_value(row_id) api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4079,7 +4138,8 @@ def create_rows( api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_params['rows'] = self._normalize_value(rows) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4142,7 +4202,8 @@ def upsert_rows( api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_params['rows'] = self._normalize_value(rows) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4207,7 +4268,8 @@ def update_rows( api_params['data'] = self._normalize_value(data) if queries is not None: api_params['queries'] = self._normalize_value(queries) - api_params['transactionId'] = self._normalize_value(transaction_id) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4405,8 +4467,10 @@ def upsert_row( if data is not None: api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4476,8 +4540,10 @@ def update_row( if data is not None: api_params['data'] = self._normalize_value(data) - api_params['permissions'] = self._normalize_value(permissions) - api_params['transactionId'] = self._normalize_value(transaction_id) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4612,8 +4678,10 @@ def decrement_row_column( if value is not None: api_params['value'] = self._normalize_value(value) - api_params['min'] = self._normalize_value(min) - api_params['transactionId'] = self._normalize_value(transaction_id) + if min is not None: + api_params['min'] = self._normalize_value(min) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4690,8 +4758,10 @@ def increment_row_column( if value is not None: api_params['value'] = self._normalize_value(value) - api_params['max'] = self._normalize_value(max) - api_params['transactionId'] = self._normalize_value(transaction_id) + if max is not None: + api_params['max'] = self._normalize_value(max) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/tokens.py b/appwrite/services/tokens.py index 0c04dfe3..bdff3a61 100644 --- a/appwrite/services/tokens.py +++ b/appwrite/services/tokens.py @@ -107,7 +107,8 @@ def create_file_token( api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -190,7 +191,8 @@ def update( api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - api_params['expire'] = self._normalize_value(expire) + if expire is not None: + api_params['expire'] = self._normalize_value(expire) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/users.py b/appwrite/services/users.py index c0e282e6..8eab2dc7 100644 --- a/appwrite/services/users.py +++ b/appwrite/services/users.py @@ -125,8 +125,10 @@ def create( api_params['userId'] = self._normalize_value(user_id) - api_params['email'] = self._normalize_value(email) - api_params['phone'] = self._normalize_value(phone) + if email is not None: + api_params['email'] = self._normalize_value(email) + if phone is not None: + api_params['phone'] = self._normalize_value(phone) if password is not None: api_params['password'] = self._normalize_value(password) if name is not None: diff --git a/appwrite/services/webhooks.py b/appwrite/services/webhooks.py index b9c99e8e..9e998f36 100644 --- a/appwrite/services/webhooks.py +++ b/appwrite/services/webhooks.py @@ -127,7 +127,8 @@ def create( api_params['authUsername'] = self._normalize_value(auth_username) if auth_password is not None: api_params['authPassword'] = self._normalize_value(auth_password) - api_params['secret'] = self._normalize_value(secret) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -330,7 +331,8 @@ def update_secret( api_path = api_path.replace('{webhookId}', str(self._normalize_value(webhook_id))) - api_params['secret'] = self._normalize_value(secret) + if secret is not None: + api_params['secret'] = self._normalize_value(secret) response = self.client.call('patch', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), From 122cd9b2dd4a79046d52f7f1eb11533f0ff2e9a9 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Wed, 22 Jul 2026 11:02:50 +0530 Subject: [PATCH 03/10] chore: update Python SDK to 22.1.0 --- CHANGELOG.md | 12 + appwrite/client.py | 4 +- appwrite/enums/database_status.py | 11 + appwrite/enums/database_type.py | 3 + appwrite/enums/project_key_scopes.py | 3 + appwrite/models/__init__.py | 32 +++ appwrite/models/activity_event.py | 33 +++ appwrite/models/app_scope.py | 27 ++ appwrite/models/app_scope_list.py | 19 ++ appwrite/models/app_secret.py | 2 +- appwrite/models/app_secret_plaintext.py | 2 +- appwrite/models/billing_plan.py | 3 + appwrite/models/database.py | 13 +- appwrite/models/database_status.py | 39 +++ .../models/database_status_connections.py | 18 ++ appwrite/models/database_status_replica.py | 24 ++ appwrite/models/database_status_volume.py | 24 ++ appwrite/models/dedicated_database.py | 159 +++++++++++ appwrite/models/dedicated_database_member.py | 24 ++ .../models/dedicated_database_replicas.py | 22 ++ .../dedicated_database_specification.py | 39 +++ .../dedicated_database_specification_list.py | 23 ++ ...edicated_database_specification_pricing.py | 27 ++ appwrite/models/oauth2_consent.py | 42 +++ appwrite/models/oauth2_consent_list.py | 19 ++ appwrite/models/oauth2_consent_token.py | 45 +++ appwrite/models/oauth2_consent_token_list.py | 19 ++ appwrite/models/project.py | 3 + appwrite/services/account.py | 267 ++++++++++++++++++ appwrite/services/apps.py | 39 ++- appwrite/services/backups.py | 17 +- appwrite/services/oauth2.py | 113 +++++++- appwrite/services/sites.py | 7 +- appwrite/services/tables_db.py | 169 ++++++++++- docs/examples/account/delete-consent-token.md | 16 ++ docs/examples/account/delete-consent.md | 15 + docs/examples/account/get-consent-token.md | 19 ++ docs/examples/account/get-consent.md | 18 ++ docs/examples/account/list-consent-tokens.md | 20 ++ docs/examples/account/list-consents.md | 19 ++ docs/examples/apps/list-o-auth-2-scopes.md | 16 ++ docs/examples/backups/create-restoration.md | 3 +- docs/examples/oauth2/authorize-post.md | 31 ++ .../examples/sites/get-deployment-download.md | 3 +- docs/examples/tablesdb/create-failover.md | 19 ++ docs/examples/tablesdb/create.md | 3 +- docs/examples/tablesdb/get-replicas.md | 18 ++ docs/examples/tablesdb/get-status.md | 18 ++ docs/examples/tablesdb/list-specifications.md | 16 ++ docs/examples/tablesdb/update.md | 3 +- pyproject.toml | 2 +- setup.py | 4 +- test/services/test_account.py | 102 +++++++ test/services/test_activities.py | 13 +- test/services/test_apps.py | 16 +- test/services/test_backups.py | 4 +- test/services/test_databases.py | 12 +- test/services/test_oauth2.py | 14 + test/services/test_organization.py | 11 +- test/services/test_project.py | 60 ++-- test/services/test_tables_db.py | 133 ++++++++- 61 files changed, 1828 insertions(+), 83 deletions(-) create mode 100644 appwrite/models/app_scope.py create mode 100644 appwrite/models/app_scope_list.py create mode 100644 appwrite/models/database_status.py create mode 100644 appwrite/models/database_status_connections.py create mode 100644 appwrite/models/database_status_replica.py create mode 100644 appwrite/models/database_status_volume.py create mode 100644 appwrite/models/dedicated_database.py create mode 100644 appwrite/models/dedicated_database_member.py create mode 100644 appwrite/models/dedicated_database_replicas.py create mode 100644 appwrite/models/dedicated_database_specification.py create mode 100644 appwrite/models/dedicated_database_specification_list.py create mode 100644 appwrite/models/dedicated_database_specification_pricing.py create mode 100644 appwrite/models/oauth2_consent.py create mode 100644 appwrite/models/oauth2_consent_list.py create mode 100644 appwrite/models/oauth2_consent_token.py create mode 100644 appwrite/models/oauth2_consent_token_list.py create mode 100644 docs/examples/account/delete-consent-token.md create mode 100644 docs/examples/account/delete-consent.md create mode 100644 docs/examples/account/get-consent-token.md create mode 100644 docs/examples/account/get-consent.md create mode 100644 docs/examples/account/list-consent-tokens.md create mode 100644 docs/examples/account/list-consents.md create mode 100644 docs/examples/apps/list-o-auth-2-scopes.md create mode 100644 docs/examples/oauth2/authorize-post.md create mode 100644 docs/examples/tablesdb/create-failover.md create mode 100644 docs/examples/tablesdb/get-replicas.md create mode 100644 docs/examples/tablesdb/get-status.md create mode 100644 docs/examples/tablesdb/list-specifications.md diff --git a/CHANGELOG.md b/CHANGELOG.md index e66e10b9..d0f3fdfd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,17 @@ # Change Log +## 22.1.0 + +* Updated: removed `new_specification` parameter from `backups.create_restoration` +* Updated: `Database.policies` and `Database.archives` are now optional +* Added: account OAuth2 consent methods `list_consents`, `get_consent`, `delete_consent` and consent token methods +* Added: `Oauth2Consent` and `Oauth2ConsentToken` models +* Added: `oauth2.authorize_post` method and `oauth2.introspect` key scope +* Added: `apps.list_o_auth2_scopes` method and `AppScope` model +* Added: geolocation, connection, and SDK attribution fields on `ActivityEvent` +* Added: `token` parameter to `sites.get_deployment_download` +* Updated: `AppSecret.secret` is always empty; the secret is returned only on creation + ## 22.0.0 * Breaking: removed `Health` service and all health models and enums diff --git a/appwrite/client.py b/appwrite/client.py index 0fc438b7..3588e3a7 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -17,11 +17,11 @@ def __init__(self): self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent' : f'AppwritePythonSDK/22.0.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent' : f'AppwritePythonSDK/22.1.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '22.0.0', + 'x-sdk-version': '22.1.0', 'X-Appwrite-Response-Format' : '1.9.5', } self._config = {} diff --git a/appwrite/enums/database_status.py b/appwrite/enums/database_status.py index 7c5f888f..ed43ed1a 100644 --- a/appwrite/enums/database_status.py +++ b/appwrite/enums/database_status.py @@ -3,4 +3,15 @@ class DatabaseStatus(Enum): PROVISIONING = "provisioning" READY = "ready" + INACTIVE = "inactive" + PAUSED = "paused" FAILED = "failed" + DELETING = "deleting" + DELETED = "deleted" + RESTORING = "restoring" + SCALING = "scaling" + UPGRADING = "upgrading" + MIGRATING = "migrating" + PAUSING = "pausing" + RESUMING = "resuming" + FAILING_OVER = "failing-over" diff --git a/appwrite/enums/database_type.py b/appwrite/enums/database_type.py index 5d2d0aeb..0b713567 100644 --- a/appwrite/enums/database_type.py +++ b/appwrite/enums/database_type.py @@ -5,3 +5,6 @@ class DatabaseType(Enum): TABLESDB = "tablesdb" DOCUMENTSDB = "documentsdb" VECTORSDB = "vectorsdb" + MYSQL = "mysql" + POSTGRESQL = "postgresql" + MONGODB = "mongodb" diff --git a/appwrite/enums/project_key_scopes.py b/appwrite/enums/project_key_scopes.py index 10099119..e29a2454 100644 --- a/appwrite/enums/project_key_scopes.py +++ b/appwrite/enums/project_key_scopes.py @@ -96,9 +96,12 @@ class ProjectKeyScopes(Enum): DEDICATEDDATABASES_EXECUTE = "dedicatedDatabases.execute" DOMAINS_READ = "domains.read" DOMAINS_WRITE = "domains.write" + WAFRULES_READ = "wafRules.read" + WAFRULES_WRITE = "wafRules.write" EVENTS_READ = "events.read" APPS_READ = "apps.read" APPS_WRITE = "apps.write" OAUTH2_READ = "oauth2.read" OAUTH2_WRITE = "oauth2.write" + OAUTH2_INTROSPECT = "oauth2.introspect" USAGE_READ = "usage.read" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 8e75504a..07a73030 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -220,6 +220,10 @@ from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits from .billing_plan_supported_addons import BillingPlanSupportedAddons from .block import Block +from .dedicated_database import DedicatedDatabase +from .database_status import DatabaseStatus +from .dedicated_database_member import DedicatedDatabaseMember +from .dedicated_database_replicas import DedicatedDatabaseReplicas from .organization import Organization from .backup_policy import BackupPolicy from .policy_deny_aliased_email import PolicyDenyAliasedEmail @@ -228,10 +232,17 @@ from .policy_deny_corporate_email import PolicyDenyCorporateEmail from .program import Program from .backup_restoration import BackupRestoration +from .dedicated_database_specification import DedicatedDatabaseSpecification +from .dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from .dedicated_database_specification_pricing import DedicatedDatabaseSpecificationPricing +from .database_status_connections import DatabaseStatusConnections +from .database_status_replica import DatabaseStatusReplica +from .database_status_volume import DatabaseStatusVolume from .usage_billing_plan import UsageBillingPlan from .app import App from .app_secret import AppSecret from .app_secret_plaintext import AppSecretPlaintext +from .app_scope import AppScope from .oauth2_authorize import Oauth2Authorize from .oauth2_approve import Oauth2Approve from .oauth2_reject import Oauth2Reject @@ -239,16 +250,21 @@ from .oauth2_device_authorization import Oauth2DeviceAuthorization from .oauth2_par import Oauth2PAR from .oauth2_token import Oauth2Token +from .oauth2_consent import Oauth2Consent +from .oauth2_consent_token import Oauth2ConsentToken from .oauth2_project import Oauth2Project from .oauth2_organization import Oauth2Organization from .oauth2_project_list import Oauth2ProjectList from .oauth2_organization_list import Oauth2OrganizationList +from .oauth2_consent_list import Oauth2ConsentList +from .oauth2_consent_token_list import Oauth2ConsentTokenList from .activity_event_list import ActivityEventList from .backup_archive_list import BackupArchiveList from .backup_policy_list import BackupPolicyList from .backup_restoration_list import BackupRestorationList from .apps_list import AppsList from .app_secret_list import AppSecretList +from .app_scope_list import AppScopeList __all__ = [ 'AppwriteModel', @@ -473,6 +489,10 @@ 'BillingPlanDedicatedDatabaseLimits', 'BillingPlanSupportedAddons', 'Block', + 'DedicatedDatabase', + 'DatabaseStatus', + 'DedicatedDatabaseMember', + 'DedicatedDatabaseReplicas', 'Organization', 'BackupPolicy', 'PolicyDenyAliasedEmail', @@ -481,10 +501,17 @@ 'PolicyDenyCorporateEmail', 'Program', 'BackupRestoration', + 'DedicatedDatabaseSpecification', + 'DedicatedDatabaseSpecificationList', + 'DedicatedDatabaseSpecificationPricing', + 'DatabaseStatusConnections', + 'DatabaseStatusReplica', + 'DatabaseStatusVolume', 'UsageBillingPlan', 'App', 'AppSecret', 'AppSecretPlaintext', + 'AppScope', 'Oauth2Authorize', 'Oauth2Approve', 'Oauth2Reject', @@ -492,14 +519,19 @@ 'Oauth2DeviceAuthorization', 'Oauth2PAR', 'Oauth2Token', + 'Oauth2Consent', + 'Oauth2ConsentToken', 'Oauth2Project', 'Oauth2Organization', 'Oauth2ProjectList', 'Oauth2OrganizationList', + 'Oauth2ConsentList', + 'Oauth2ConsentTokenList', 'ActivityEventList', 'BackupArchiveList', 'BackupPolicyList', 'BackupRestorationList', 'AppsList', 'AppSecretList', + 'AppScopeList', ] diff --git a/appwrite/models/activity_event.py b/appwrite/models/activity_event.py index 11265c1d..eddec37d 100644 --- a/appwrite/models/activity_event.py +++ b/appwrite/models/activity_event.py @@ -37,6 +37,24 @@ class ActivityEvent(AppwriteModel): API mode when event triggered. country : str Location. + continentcode : str + Continent code. + city : str + City name. + subdivisions : str + Region/state chain. + isp : str + Internet service provider. + autonomoussystemnumber : str + Autonomous System Number (ASN). + autonomoussystemorganization : str + Organization that owns the ASN. + connectiontype : str + Connection type (e.g. cable, cellular, corporate). + connectionusagetype : str + User type (e.g. residential, business, hosting). + connectionorganization : str + Registered organization of the IP. time : str Log creation date in ISO 8601 format. projectid : str @@ -45,6 +63,10 @@ class ActivityEvent(AppwriteModel): Team ID. hostname : str Hostname. + sdk : str + Name of the SDK that triggered the event. + sdkversion : str + Version of the SDK that triggered the event. """ id: str = Field(..., alias='$id') actortype: str = Field(..., alias='actorType') @@ -60,7 +82,18 @@ class ActivityEvent(AppwriteModel): ip: str = Field(..., alias='ip') mode: str = Field(..., alias='mode') country: str = Field(..., alias='country') + continentcode: str = Field(..., alias='continentCode') + city: str = Field(..., alias='city') + subdivisions: str = Field(..., alias='subdivisions') + isp: str = Field(..., alias='isp') + autonomoussystemnumber: str = Field(..., alias='autonomousSystemNumber') + autonomoussystemorganization: str = Field(..., alias='autonomousSystemOrganization') + connectiontype: str = Field(..., alias='connectionType') + connectionusagetype: str = Field(..., alias='connectionUsageType') + connectionorganization: str = Field(..., alias='connectionOrganization') time: str = Field(..., alias='time') projectid: str = Field(..., alias='projectId') teamid: str = Field(..., alias='teamId') hostname: str = Field(..., alias='hostname') + sdk: str = Field(..., alias='sdk') + sdkversion: str = Field(..., alias='sdkVersion') diff --git a/appwrite/models/app_scope.py b/appwrite/models/app_scope.py new file mode 100644 index 00000000..4dca2ae2 --- /dev/null +++ b/appwrite/models/app_scope.py @@ -0,0 +1,27 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class AppScope(AppwriteModel): + """ + AppScope + + Attributes + ---------- + value : str + Scope value as requested by apps. + description : str + Human-readable description of what the scope grants. + type : str + What the scope grants access to. One of `account`, `project`, or `organization`. Only `project` and `organization` scopes are installable. + category : str + Scope category, used to group scopes on consent and installation screens. + deprecated : bool + Whether the scope is deprecated. Deprecated scopes can still be requested but should not be offered for new grants. + """ + value: str = Field(..., alias='value') + description: str = Field(..., alias='description') + type: str = Field(..., alias='type') + category: str = Field(..., alias='category') + deprecated: bool = Field(..., alias='deprecated') diff --git a/appwrite/models/app_scope_list.py b/appwrite/models/app_scope_list.py new file mode 100644 index 00000000..f92908e7 --- /dev/null +++ b/appwrite/models/app_scope_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .app_scope import AppScope + +class AppScopeList(AppwriteModel): + """ + App scopes list + + Attributes + ---------- + total : float + Total number of scopes that matched your query. + scopes : List[AppScope] + List of scopes. + """ + total: float = Field(..., alias='total') + scopes: List[AppScope] = Field(..., alias='scopes') diff --git a/appwrite/models/app_secret.py b/appwrite/models/app_secret.py index dc7def83..348b2cbf 100644 --- a/appwrite/models/app_secret.py +++ b/appwrite/models/app_secret.py @@ -18,7 +18,7 @@ class AppSecret(AppwriteModel): appid : str Application ID this secret belongs to. secret : str - Hashed application client secret. + Always empty. The application client secret is returned only once, in the response of the createSecret method. hint : str Last few characters of the client secret, used to help identify it. createdbyid : str diff --git a/appwrite/models/app_secret_plaintext.py b/appwrite/models/app_secret_plaintext.py index ec6d9ae5..18a32d13 100644 --- a/appwrite/models/app_secret_plaintext.py +++ b/appwrite/models/app_secret_plaintext.py @@ -18,7 +18,7 @@ class AppSecretPlaintext(AppwriteModel): appid : str Application ID this secret belongs to. secret : str - Application client secret. Returned in full only when the secret is created; subsequent reads return a masked value. + Application client secret. Returned only when the secret is created; subsequent reads always return an empty value. hint : str Last few characters of the client secret, used to help identify it. createdbyid : str diff --git a/appwrite/models/billing_plan.py b/appwrite/models/billing_plan.py index 64db521b..c37db9d3 100644 --- a/appwrite/models/billing_plan.py +++ b/appwrite/models/billing_plan.py @@ -40,6 +40,8 @@ class BillingPlan(AppwriteModel): Members webhooks : float Webhooks + wafrules : float + Maximum WAF rules per project projects : float Projects platforms : float @@ -165,6 +167,7 @@ class BillingPlan(AppwriteModel): screenshotsgenerated: float = Field(..., alias='screenshotsGenerated') members: float = Field(..., alias='members') webhooks: float = Field(..., alias='webhooks') + wafrules: float = Field(..., alias='wafRules') projects: float = Field(..., alias='projects') platforms: float = Field(..., alias='platforms') users: float = Field(..., alias='users') diff --git a/appwrite/models/database.py b/appwrite/models/database.py index b491a89a..f83198fd 100644 --- a/appwrite/models/database.py +++ b/appwrite/models/database.py @@ -26,10 +26,12 @@ class Database(AppwriteModel): type : DatabaseType Database type. status : Optional[DatabaseStatus] - Database status. Possible values: `provisioning`, `ready` or `failed` - policies : List[BackupPolicy] + Dedicated database lifecycle status. Null when the database has no valid dedicated backing. + replicas : Optional[float] + Number of secondary high availability replicas, excluding the primary. Null when backing configuration is unavailable. + policies : Optional[List[BackupPolicy]] Database backup policies. - archives : List[BackupArchive] + archives : Optional[List[BackupArchive]] Database backup archives. """ id: str = Field(..., alias='$id') @@ -39,5 +41,6 @@ class Database(AppwriteModel): enabled: bool = Field(..., alias='enabled') type: DatabaseType = Field(..., alias='type') status: Optional[DatabaseStatus] = Field(default=None, alias='status') - policies: List[BackupPolicy] = Field(..., alias='policies') - archives: List[BackupArchive] = Field(..., alias='archives') + replicas: Optional[float] = Field(default=None, alias='replicas') + policies: Optional[List[BackupPolicy]] = Field(default=None, alias='policies') + archives: Optional[List[BackupArchive]] = Field(default=None, alias='archives') diff --git a/appwrite/models/database_status.py b/appwrite/models/database_status.py new file mode 100644 index 00000000..dd469917 --- /dev/null +++ b/appwrite/models/database_status.py @@ -0,0 +1,39 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .database_status_connections import DatabaseStatusConnections +from .database_status_replica import DatabaseStatusReplica +from .database_status_volume import DatabaseStatusVolume + +class DatabaseStatus(AppwriteModel): + """ + Status + + Attributes + ---------- + health : str + Overall health status: healthy, degraded, or unhealthy. + ready : bool + Whether the database is ready to accept connections. + engine : str + Database engine: postgresql, mysql, mariadb, or mongodb. + version : str + Database engine version. + uptime : float + Database uptime in seconds. + connections : DatabaseStatusConnections + Connection statistics. + replicas : List[DatabaseStatusReplica] + List of database replicas and their status. + volumes : List[DatabaseStatusVolume] + Storage volume information. + """ + health: str = Field(..., alias='health') + ready: bool = Field(..., alias='ready') + engine: str = Field(..., alias='engine') + version: str = Field(..., alias='version') + uptime: float = Field(..., alias='uptime') + connections: DatabaseStatusConnections = Field(..., alias='connections') + replicas: List[DatabaseStatusReplica] = Field(..., alias='replicas') + volumes: List[DatabaseStatusVolume] = Field(..., alias='volumes') diff --git a/appwrite/models/database_status_connections.py b/appwrite/models/database_status_connections.py new file mode 100644 index 00000000..fe335596 --- /dev/null +++ b/appwrite/models/database_status_connections.py @@ -0,0 +1,18 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DatabaseStatusConnections(AppwriteModel): + """ + Connections + + Attributes + ---------- + current : float + Current number of active connections. + max : float + Maximum allowed connections. + """ + current: float = Field(..., alias='current') + max: float = Field(..., alias='max') diff --git a/appwrite/models/database_status_replica.py b/appwrite/models/database_status_replica.py new file mode 100644 index 00000000..73cf79e4 --- /dev/null +++ b/appwrite/models/database_status_replica.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DatabaseStatusReplica(AppwriteModel): + """ + Replica + + Attributes + ---------- + index : float + StatefulSet pod index (0 = primary, 1+ = replicas). + role : str + Replica role: primary or replica. + healthy : bool + Whether the replica is healthy. + lagseconds : Optional[float] + Replication lag in seconds (null for primary). + """ + index: float = Field(..., alias='index') + role: str = Field(..., alias='role') + healthy: bool = Field(..., alias='healthy') + lagseconds: Optional[float] = Field(default=None, alias='lagSeconds') diff --git a/appwrite/models/database_status_volume.py b/appwrite/models/database_status_volume.py new file mode 100644 index 00000000..0b14ba8c --- /dev/null +++ b/appwrite/models/database_status_volume.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DatabaseStatusVolume(AppwriteModel): + """ + Volume + + Attributes + ---------- + path : str + Mount path of the volume. + usedpercent : str + Percentage of storage used. + available : str + Available storage space. + mounted : bool + Whether the volume is mounted. + """ + path: str = Field(..., alias='path') + usedpercent: str = Field(..., alias='usedPercent') + available: str = Field(..., alias='available') + mounted: bool = Field(..., alias='mounted') diff --git a/appwrite/models/dedicated_database.py b/appwrite/models/dedicated_database.py new file mode 100644 index 00000000..9f943228 --- /dev/null +++ b/appwrite/models/dedicated_database.py @@ -0,0 +1,159 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DedicatedDatabase(AppwriteModel): + """ + DedicatedDatabase + + Attributes + ---------- + id : str + Dedicated database ID. + createdat : str + Database creation time in ISO 8601 format. + updatedat : str + Database update date in ISO 8601 format. + projectid : str + Project ID that owns this database. + name : str + Database display name. + api : str + Product API that owns this database: tablesdb, documentsdb, vectorsdb, mysql, postgresql, or mongodb. + engine : str + Database engine: postgresql, mysql, mariadb, or mongodb. + version : str + Database engine version. + specification : str + Specification identifier. + backend : str + Database backend provider. Possible values: prisma, edge. + hostname : str + Database hostname for connections. + connectionport : float + Database port for connections. + connectionuser : str + Database username for connections. + connectionpassword : str + Database password for connections. + connectionstring : str + Full database connection string (URI format). + ssl : bool + Whether SSL/TLS is required for client connections. + status : str + Database status. Possible values: provisioning, ready, inactive, paused, failed, deleted, restoring, scaling. + containerstatus : str + Container status for lifecycle-managed database runtimes: active or inactive. + lastaccessedat : Optional[str] + Last activity timestamp in ISO 8601 format. + idleuntil : Optional[str] + Display-only timestamp when the database is expected to be considered idle (ISO 8601 format). Derived from last activity; lifecycle transitions are driven by lifecycleState. + lifecyclestate : str + Idle-lifecycle state of the database. Possible values: active, warm, cold, hibernated. + idletimeoutminutes : float + Minutes of inactivity before container scales to zero. + cpu : float + CPU allocated in millicores. + memory : float + Memory allocated in MB. + storage : float + Storage allocated in GB. + storageclass : str + Storage class. Currently always 'ssd'; DigitalOcean exposes a single block-storage class. + storagemaxgb : float + Maximum storage allowed in GB. 0 means use system default. + nodepool : str + Kubernetes node pool where the database is scheduled. + replicas : float + Number of high availability replicas. High availability is enabled when greater than 0. + syncmode : str + Replication sync mode: async, sync, or quorum. + crossregionreplicas : float + Number of cross-region replicas. Cross-region availability is enabled when greater than 0. + networkmaxconnections : float + Maximum concurrent connections. + networkidletimeoutseconds : float + Connection idle timeout in seconds. + networkipallowlist : List[Any] + IP addresses/CIDR ranges allowed to connect. + backupenabled : bool + Whether automatic backups are enabled. + pitr : bool + Whether point-in-time recovery is enabled. + pitrretentiondays : float + Number of days to retain PITR data. + storageautoscaling : bool + Whether automatic storage expansion is enabled. + storageautoscalingthresholdpercent : float + Storage usage percentage that triggers automatic expansion. + storageautoscalingmaxgb : float + Maximum storage size in GB for autoscaling. 0 means no limit. + maintenancewindowday : str + Day of the week for the maintenance window. Possible values: sun, mon, tue, wed, thu, fri, sat. + maintenancewindowhourutc : float + Hour in UTC (0-23) when the maintenance window starts. + metricsenabled : bool + Whether metrics collection is enabled. + sqlapienabled : bool + Whether the SQL API sidecar is enabled for this database. + sqlapiallowedstatements : List[Any] + Statement types accepted by the SQL API. Defaults to read/write DML only; DDL/DCL types (CREATE, ALTER, DROP, TRUNCATE, GRANT, REVOKE) are opt-in per database. Allowed values: SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, DROP, TRUNCATE, GRANT, REVOKE. + sqlapimaxrows : float + Maximum rows returned per SQL API execution. Results larger than this are truncated. + sqlapimaxbytes : float + Maximum serialised SQL API result payload in bytes. Results larger than this are truncated. + sqlapitimeoutseconds : float + Maximum server-side SQL API execution time in seconds before the query is cancelled. + error : str + Error message if status is failed. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + projectid: str = Field(..., alias='projectId') + name: str = Field(..., alias='name') + api: str = Field(..., alias='api') + engine: str = Field(..., alias='engine') + version: str = Field(..., alias='version') + specification: str = Field(..., alias='specification') + backend: str = Field(..., alias='backend') + hostname: str = Field(..., alias='hostname') + connectionport: float = Field(..., alias='connectionPort') + connectionuser: str = Field(..., alias='connectionUser') + connectionpassword: str = Field(..., alias='connectionPassword') + connectionstring: str = Field(..., alias='connectionString') + ssl: bool = Field(..., alias='ssl') + status: str = Field(..., alias='status') + containerstatus: str = Field(..., alias='containerStatus') + lastaccessedat: Optional[str] = Field(default=None, alias='lastAccessedAt') + idleuntil: Optional[str] = Field(default=None, alias='idleUntil') + lifecyclestate: str = Field(..., alias='lifecycleState') + idletimeoutminutes: float = Field(..., alias='idleTimeoutMinutes') + cpu: float = Field(..., alias='cpu') + memory: float = Field(..., alias='memory') + storage: float = Field(..., alias='storage') + storageclass: str = Field(..., alias='storageClass') + storagemaxgb: float = Field(..., alias='storageMaxGb') + nodepool: str = Field(..., alias='nodePool') + replicas: float = Field(..., alias='replicas') + syncmode: str = Field(..., alias='syncMode') + crossregionreplicas: float = Field(..., alias='crossRegionReplicas') + networkmaxconnections: float = Field(..., alias='networkMaxConnections') + networkidletimeoutseconds: float = Field(..., alias='networkIdleTimeoutSeconds') + networkipallowlist: List[Any] = Field(..., alias='networkIPAllowlist') + backupenabled: bool = Field(..., alias='backupEnabled') + pitr: bool = Field(..., alias='pitr') + pitrretentiondays: float = Field(..., alias='pitrRetentionDays') + storageautoscaling: bool = Field(..., alias='storageAutoscaling') + storageautoscalingthresholdpercent: float = Field(..., alias='storageAutoscalingThresholdPercent') + storageautoscalingmaxgb: float = Field(..., alias='storageAutoscalingMaxGb') + maintenancewindowday: str = Field(..., alias='maintenanceWindowDay') + maintenancewindowhourutc: float = Field(..., alias='maintenanceWindowHourUtc') + metricsenabled: bool = Field(..., alias='metricsEnabled') + sqlapienabled: bool = Field(..., alias='sqlApiEnabled') + sqlapiallowedstatements: List[Any] = Field(..., alias='sqlApiAllowedStatements') + sqlapimaxrows: float = Field(..., alias='sqlApiMaxRows') + sqlapimaxbytes: float = Field(..., alias='sqlApiMaxBytes') + sqlapitimeoutseconds: float = Field(..., alias='sqlApiTimeoutSeconds') + error: str = Field(..., alias='error') diff --git a/appwrite/models/dedicated_database_member.py b/appwrite/models/dedicated_database_member.py new file mode 100644 index 00000000..6cb4daa3 --- /dev/null +++ b/appwrite/models/dedicated_database_member.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DedicatedDatabaseMember(AppwriteModel): + """ + Member + + Attributes + ---------- + id : str + Member identifier. + role : str + Member role. Possible values: primary (accepts reads and writes), replica (read-only follower). + status : str + Member pod status. Possible values: provisioning (pod missing or Pending), starting (Running but not Ready), active (Running and Ready), failed (Failed phase or CrashLoopBackOff container), or the lowercased pod phase reported by the cluster. + lagseconds : float + Replication lag in seconds. + """ + id: str = Field(..., alias='$id') + role: str = Field(..., alias='role') + status: str = Field(..., alias='status') + lagseconds: float = Field(..., alias='lagSeconds') diff --git a/appwrite/models/dedicated_database_replicas.py b/appwrite/models/dedicated_database_replicas.py new file mode 100644 index 00000000..fa19a87a --- /dev/null +++ b/appwrite/models/dedicated_database_replicas.py @@ -0,0 +1,22 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_member import DedicatedDatabaseMember + +class DedicatedDatabaseReplicas(AppwriteModel): + """ + Replicas + + Attributes + ---------- + replicas : float + Number of configured replicas. Zero means high availability is disabled. + syncmode : str + Replication sync mode. Possible values: async (asynchronous, fastest), sync (synchronous, strong consistency), quorum (quorum-based, majority of replicas must confirm). + members : List[DedicatedDatabaseMember] + Per-pod statuses for the primary and every replica. + """ + replicas: float = Field(..., alias='replicas') + syncmode: str = Field(..., alias='syncMode') + members: List[DedicatedDatabaseMember] = Field(..., alias='members') diff --git a/appwrite/models/dedicated_database_specification.py b/appwrite/models/dedicated_database_specification.py new file mode 100644 index 00000000..d5f37295 --- /dev/null +++ b/appwrite/models/dedicated_database_specification.py @@ -0,0 +1,39 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DedicatedDatabaseSpecification(AppwriteModel): + """ + Specification + + Attributes + ---------- + slug : str + Specification slug. Use this value when creating a dedicated database. + name : str + Human readable specification name. + price : float + Monthly price of the specification in USD. + cpu : float + Allocated CPU in millicores. + memory : float + Allocated memory in MB. + maxconnections : float + Maximum number of concurrent connections. + includedstorage : float + Included storage in GB before overage charges apply. + includedbandwidth : float + Included bandwidth in GB before overage charges apply. + enabled : bool + Whether the specification is available on the current plan. + """ + slug: str = Field(..., alias='slug') + name: str = Field(..., alias='name') + price: float = Field(..., alias='price') + cpu: float = Field(..., alias='cpu') + memory: float = Field(..., alias='memory') + maxconnections: float = Field(..., alias='maxConnections') + includedstorage: float = Field(..., alias='includedStorage') + includedbandwidth: float = Field(..., alias='includedBandwidth') + enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/dedicated_database_specification_list.py b/appwrite/models/dedicated_database_specification_list.py new file mode 100644 index 00000000..8cbd905d --- /dev/null +++ b/appwrite/models/dedicated_database_specification_list.py @@ -0,0 +1,23 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_specification import DedicatedDatabaseSpecification +from .dedicated_database_specification_pricing import DedicatedDatabaseSpecificationPricing + +class DedicatedDatabaseSpecificationList(AppwriteModel): + """ + SpecificationList + + Attributes + ---------- + specifications : List[DedicatedDatabaseSpecification] + List of dedicated database specifications. + total : float + Total number of specifications. + pricing : DedicatedDatabaseSpecificationPricing + Overage and add-on pricing shared across all specifications. + """ + specifications: List[DedicatedDatabaseSpecification] = Field(..., alias='specifications') + total: float = Field(..., alias='total') + pricing: DedicatedDatabaseSpecificationPricing = Field(..., alias='pricing') diff --git a/appwrite/models/dedicated_database_specification_pricing.py b/appwrite/models/dedicated_database_specification_pricing.py new file mode 100644 index 00000000..43d3b1e7 --- /dev/null +++ b/appwrite/models/dedicated_database_specification_pricing.py @@ -0,0 +1,27 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DedicatedDatabaseSpecificationPricing(AppwriteModel): + """ + SpecificationPricing + + Attributes + ---------- + storageoveragerate : float + Price per GB of storage above the included amount, per month, in USD. + bandwidthoveragerate : float + Price per GB of bandwidth above the included amount, per month, in USD. + replicarate : float + High availability replica price as a fraction of the specification cost. + crossregionreplicarate : float + Cross-region replica price as a fraction of the specification cost. + pitrrate : float + Point-in-time recovery price as a fraction of the specification cost. + """ + storageoveragerate: float = Field(..., alias='storageOverageRate') + bandwidthoveragerate: float = Field(..., alias='bandwidthOverageRate') + replicarate: float = Field(..., alias='replicaRate') + crossregionreplicarate: float = Field(..., alias='crossRegionReplicaRate') + pitrrate: float = Field(..., alias='pitrRate') diff --git a/appwrite/models/oauth2_consent.py b/appwrite/models/oauth2_consent.py new file mode 100644 index 00000000..6675856b --- /dev/null +++ b/appwrite/models/oauth2_consent.py @@ -0,0 +1,42 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Oauth2Consent(AppwriteModel): + """ + OAuth2 Consent + + Attributes + ---------- + id : str + Consent ID. + createdat : str + Consent creation time in ISO 8601 format. + updatedat : str + Consent update date in ISO 8601 format. + userid : str + ID of the user the consent belongs to. + appid : str + ID of the registered app the consent was given to. Empty for URL-form (CIMD) clients. + cimdurl : str + Client ID metadata document URL of the client the consent was given to. Empty for registered apps. + scopes : List[Any] + OAuth2 scopes the user consented to. + resources : List[Any] + RFC 8707 resource indicators the user consented to. + authorizationdetails : str + Authorization details the user consented to, as a JSON string. Each entry has a `type` plus project-defined fields. + expire : str + Consent expiration time in ISO 8601 format. Empty when the consent has no token-bound expiry yet. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + userid: str = Field(..., alias='userId') + appid: str = Field(..., alias='appId') + cimdurl: str = Field(..., alias='cimdUrl') + scopes: List[Any] = Field(..., alias='scopes') + resources: List[Any] = Field(..., alias='resources') + authorizationdetails: str = Field(..., alias='authorizationDetails') + expire: str = Field(..., alias='expire') diff --git a/appwrite/models/oauth2_consent_list.py b/appwrite/models/oauth2_consent_list.py new file mode 100644 index 00000000..610353b6 --- /dev/null +++ b/appwrite/models/oauth2_consent_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .oauth2_consent import Oauth2Consent + +class Oauth2ConsentList(AppwriteModel): + """ + OAuth2 consents list + + Attributes + ---------- + total : float + Total number of consents that matched your query. + consents : List[Oauth2Consent] + List of consents. + """ + total: float = Field(..., alias='total') + consents: List[Oauth2Consent] = Field(..., alias='consents') diff --git a/appwrite/models/oauth2_consent_token.py b/appwrite/models/oauth2_consent_token.py new file mode 100644 index 00000000..2fd26ca5 --- /dev/null +++ b/appwrite/models/oauth2_consent_token.py @@ -0,0 +1,45 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Oauth2ConsentToken(AppwriteModel): + """ + OAuth2 Consent Token + + Attributes + ---------- + id : str + Token family ID. + createdat : str + Token creation time in ISO 8601 format. + updatedat : str + Token update date in ISO 8601 format. Refreshing the token family updates this. + consentid : str + ID of the consent the token family was issued under. + userid : str + ID of the user the token family belongs to. + appid : str + ID of the registered app the token family was issued to. Empty for URL-form (CIMD) clients. + cimdurl : str + Client ID metadata document URL of the client the token family was issued to. Empty for registered apps. + scopes : List[Any] + OAuth2 scopes granted on the token family. + resources : List[Any] + RFC 8707 resource indicators granted on the token family. + authorizationdetails : str + Authorization details granted on the token family, as a JSON string. Each entry has a `type` plus project-defined fields. + expire : str + Expiration time of the current access token of this family in ISO 8601 format. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + consentid: str = Field(..., alias='consentId') + userid: str = Field(..., alias='userId') + appid: str = Field(..., alias='appId') + cimdurl: str = Field(..., alias='cimdUrl') + scopes: List[Any] = Field(..., alias='scopes') + resources: List[Any] = Field(..., alias='resources') + authorizationdetails: str = Field(..., alias='authorizationDetails') + expire: str = Field(..., alias='expire') diff --git a/appwrite/models/oauth2_consent_token_list.py b/appwrite/models/oauth2_consent_token_list.py new file mode 100644 index 00000000..e4864cdb --- /dev/null +++ b/appwrite/models/oauth2_consent_token_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .oauth2_consent_token import Oauth2ConsentToken + +class Oauth2ConsentTokenList(AppwriteModel): + """ + OAuth2 consent tokens list + + Attributes + ---------- + total : float + Total number of tokens that matched your query. + tokens : List[Oauth2ConsentToken] + List of tokens. + """ + total: float = Field(..., alias='total') + tokens: List[Oauth2ConsentToken] = Field(..., alias='tokens') diff --git a/appwrite/models/project.py b/appwrite/models/project.py index 38e41404..3dd2ca01 100644 --- a/appwrite/models/project.py +++ b/appwrite/models/project.py @@ -69,6 +69,8 @@ class Project(AppwriteModel): Project blocks information consoleaccessedat : str Last time the project was accessed via console. Used with plan's projectInactivityDays to determine if project is paused. + wafenabled : bool + Whether WAF enforcement is enabled for the project. billinglimits : Optional[BillingLimits] Billing limits reached oauth2serverenabled : Optional[bool] @@ -129,6 +131,7 @@ class Project(AppwriteModel): protocols: List[ProjectProtocol] = Field(..., alias='protocols') blocks: List[Block] = Field(..., alias='blocks') consoleaccessedat: str = Field(..., alias='consoleAccessedAt') + wafenabled: bool = Field(..., alias='wafEnabled') billinglimits: Optional[BillingLimits] = Field(default=None, alias='billingLimits') oauth2serverenabled: Optional[bool] = Field(default=None, alias='oAuth2ServerEnabled') oauth2serverauthorizationurl: Optional[str] = Field(default=None, alias='oAuth2ServerAuthorizationUrl') diff --git a/appwrite/services/account.py b/appwrite/services/account.py index 5af533a9..492d9102 100644 --- a/appwrite/services/account.py +++ b/appwrite/services/account.py @@ -4,6 +4,10 @@ from ..exception import AppwriteException from appwrite.utils.deprecated import deprecated from ..models.user import User +from ..models.oauth2_consent_list import Oauth2ConsentList +from ..models.oauth2_consent import Oauth2Consent +from ..models.oauth2_consent_token_list import Oauth2ConsentTokenList +from ..models.oauth2_consent_token import Oauth2ConsentToken from ..models.identity_list import IdentityList from ..models.jwt import Jwt from ..models.log_list import LogList @@ -124,6 +128,269 @@ def create( return User.with_data(response, model_type) + def list_consents( + self, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> Oauth2ConsentList: + """ + Get a list of the OAuth2 consents the current user has given to third-party apps. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + Oauth2ConsentList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents' + api_params = {} + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2ConsentList) + + + def get_consent( + self, + consent_id: str + ) -> Oauth2Consent: + """ + Get an OAuth2 consent the current user has given to a third-party app by its unique ID. + + Parameters + ---------- + consent_id : str + Consent unique ID. + + Returns + ------- + Oauth2Consent + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents/{consentId}' + api_params = {} + if consent_id is None: + raise AppwriteException('Missing required parameter: "consent_id"') + + api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2Consent) + + + def delete_consent( + self, + consent_id: str + ) -> Dict[str, Any]: + """ + Delete an OAuth2 consent by its unique ID. All token families issued under the consent are revoked, and the app must ask for consent again to regain access. + + Parameters + ---------- + consent_id : str + Consent unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents/{consentId}' + api_params = {} + if consent_id is None: + raise AppwriteException('Missing required parameter: "consent_id"') + + api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + + def list_consent_tokens( + self, + consent_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> Oauth2ConsentTokenList: + """ + Get a list of the token families issued under an OAuth2 consent. Each entry represents one authorized device or session; the token secrets themselves are never returned. + + Parameters + ---------- + consent_id : str + Consent unique ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + Oauth2ConsentTokenList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents/{consentId}/tokens' + api_params = {} + if consent_id is None: + raise AppwriteException('Missing required parameter: "consent_id"') + + api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2ConsentTokenList) + + + def get_consent_token( + self, + consent_id: str, + token_id: str + ) -> Oauth2ConsentToken: + """ + Get a token family issued under an OAuth2 consent by its unique ID. The token secrets themselves are never returned. + + Parameters + ---------- + consent_id : str + Consent unique ID. + token_id : str + Token unique ID. + + Returns + ------- + Oauth2ConsentToken + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents/{consentId}/tokens/{tokenId}' + api_params = {} + if consent_id is None: + raise AppwriteException('Missing required parameter: "consent_id"') + + if token_id is None: + raise AppwriteException('Missing required parameter: "token_id"') + + api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) + api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2ConsentToken) + + + def delete_consent_token( + self, + consent_id: str, + token_id: str + ) -> Dict[str, Any]: + """ + Delete a token family issued under an OAuth2 consent by its unique ID. The access and refresh tokens of the family stop working immediately; other token families and the consent itself are unaffected. + + Parameters + ---------- + consent_id : str + Consent unique ID. + token_id : str + Token unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/account/consents/{consentId}/tokens/{tokenId}' + api_params = {} + if consent_id is None: + raise AppwriteException('Missing required parameter: "consent_id"') + + if token_id is None: + raise AppwriteException('Missing required parameter: "token_id"') + + api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) + api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + def update_email( self, email: str, diff --git a/appwrite/services/apps.py b/appwrite/services/apps.py index ab3e9110..8b8e3285 100644 --- a/appwrite/services/apps.py +++ b/appwrite/services/apps.py @@ -5,6 +5,7 @@ from appwrite.utils.deprecated import deprecated from ..models.apps_list import AppsList from ..models.app import App +from ..models.app_scope_list import AppScopeList from ..models.app_secret_list import AppSecretList from ..models.app_secret_plaintext import AppSecretPlaintext from ..models.app_secret import AppSecret @@ -88,7 +89,7 @@ def create( name : str Application name. redirect_uris : List[str] - Redirect URIs (array of valid URLs). + Redirect URIs. Each must be an https URL, an http loopback URL (localhost, 127.0.0.1, [::1]), or a private-use scheme URI (e.g. com.example.app:/oauth), and must not contain a fragment. description : Optional[str] Application description shown to users during OAuth2 consent. client_uri : Optional[str] @@ -112,7 +113,7 @@ def create( data_deletion_url : Optional[str] Application data deletion URL shown to users during OAuth2 consent. post_logout_redirect_uris : Optional[List[str]] - Post-logout redirect URIs for OpenID Connect RP-Initiated Logout (array of valid URLs). After ending the user session, the logout endpoint only redirects to URIs in this list. + Post-logout redirect URIs for OpenID Connect RP-Initiated Logout. Each must be an https URL, an http loopback URL, or a private-use scheme URI, and must not contain a fragment. After ending the user session, the logout endpoint only redirects to URIs in this list. enabled : Optional[bool] Is application enabled? type : Optional[str] @@ -190,6 +191,34 @@ def create( return self._parse_response(response, model=App) + def list_o_auth2_scopes( + self + ) -> AppScopeList: + """ + List scopes an application can request during the OAuth2 flow. + + Returns + ------- + AppScopeList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/scopes/oauth2' + api_params = {} + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppScopeList) + + def get( self, app_id: str @@ -200,7 +229,7 @@ def get( Parameters ---------- app_id : str - Application unique ID. + Application unique ID or HTTPS client ID metadata document URL. Returns ------- @@ -284,9 +313,9 @@ def update( enabled : Optional[bool] Is application enabled? redirect_uris : Optional[List[str]] - Redirect URIs (array of valid URLs). + Redirect URIs. Each must be an https URL, an http loopback URL (localhost, 127.0.0.1, [::1]), or a private-use scheme URI (e.g. com.example.app:/oauth), and must not contain a fragment. post_logout_redirect_uris : Optional[List[str]] - Post-logout redirect URIs for OpenID Connect RP-Initiated Logout (array of valid URLs). After ending the user session, the logout endpoint only redirects to URIs in this list. + Post-logout redirect URIs for OpenID Connect RP-Initiated Logout. Each must be an https URL, an http loopback URL, or a private-use scheme URI, and must not contain a fragment. After ending the user session, the logout endpoint only redirects to URIs in this list. type : Optional[str] OAuth2 client type. Use `public` for SPAs, mobile, and native apps that cannot keep a `client_secret` — PKCE is then required at the token endpoint. Use `confidential` for server-side clients that present a `client_secret`. Defaults to `confidential`. device_flow : Optional[bool] diff --git a/appwrite/services/backups.py b/appwrite/services/backups.py index 5aac7329..c8b782c5 100644 --- a/appwrite/services/backups.py +++ b/appwrite/services/backups.py @@ -434,13 +434,18 @@ def create_restoration( archive_id: str, services: List[BackupServices], new_resource_id: Optional[str] = None, - new_resource_name: Optional[str] = None, - new_specification: Optional[str] = None + new_resource_name: Optional[str] = None ) -> BackupRestoration: """ Create and trigger a new restoration for a backup on a project. - When restoring a DocumentsDB or VectorsDB database to a new resource, pass `newSpecification` to provision the restored database on a different specification than the archived one (for example, restoring onto a larger or smaller dedicated database). Use `serverless` to restore onto the shared pool, or a dedicated specification slug to restore onto a dedicated database of that size. The specification must be permitted by the organization's plan. `newSpecification` is not supported for legacy/TablesDB databases or for bucket restores. + For a backup of one database, the restoration resolves its destination before it is queued. Pass `newResourceId` to restore into that database ID, including the archived database ID to overwrite it. When `newResourceId` is omitted, a new database ID is generated and returned in `options`. + + The restoration migration records the archived database in `resourceId` and `resourceType`, and the resolved database in `destinationResourceId` and `destinationResourceType`. Database types are stored canonically as `database`, `documentsdb`, or `vectorsdb`. Project-wide restorations leave these fields empty because they do not have a single source or destination database. + + To list every migration related to one database, use its canonical type in a nested `OR(AND(...), AND(...), AND(...))` across the root, parent, and destination relation pairs: `(resourceType, resourceId)`, `(parentResourceType, parentResourceId)`, and `(destinationResourceType, destinationResourceId)`. Legacy and TablesDB databases use `database`; the operational `resourceType` of a table migration is not rewritten to `tablesdb`. + + When restoring a DocumentsDB or VectorsDB database to a new resource from a dedicated source, the restore provisions a fresh dedicated backing database at the source database's own specification. Parameters @@ -450,11 +455,9 @@ def create_restoration( services : List[BackupServices] Array of services to restore new_resource_id : Optional[str] - Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + Destination resource ID. Omit to generate a new ID, or pass the archived resource ID to overwrite it. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. new_resource_name : Optional[str] Database name. Max length: 128 chars. - new_specification : Optional[str] - Specification to provision the restored database on, when restoring a DocumentsDB or VectorsDB database to a new resource. Defaults to the archived database's specification. Use `serverless` for the shared pool or a dedicated specification slug. Returns ------- @@ -482,8 +485,6 @@ def create_restoration( api_params['newResourceId'] = self._normalize_value(new_resource_id) if new_resource_name is not None: api_params['newResourceName'] = self._normalize_value(new_resource_name) - if new_specification is not None: - api_params['newSpecification'] = self._normalize_value(new_specification) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/oauth2.py b/appwrite/services/oauth2.py index 21612207..cf7f0bc6 100644 --- a/appwrite/services/oauth2.py +++ b/appwrite/services/oauth2.py @@ -91,7 +91,7 @@ def authorize( Parameters ---------- client_id : Optional[str] - OAuth2 client ID. + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. redirect_uri : Optional[str] Redirect URI where visitor will be redirected after authorization, whether successful or not. response_type : Optional[str] @@ -170,6 +170,109 @@ def authorize( return self._parse_response(response, model=Oauth2Authorize) + def authorize_post( + self, + client_id: Optional[str] = None, + redirect_uri: Optional[str] = None, + response_type: Optional[str] = None, + scope: Optional[str] = None, + state: Optional[str] = None, + nonce: Optional[str] = None, + code_challenge: Optional[str] = None, + code_challenge_method: Optional[str] = None, + prompt: Optional[str] = None, + max_age: Optional[float] = None, + authorization_details: Optional[str] = None, + resource: Optional[str] = None, + audience: Optional[str] = None, + request_uri: Optional[str] = None + ) -> Oauth2Authorize: + """ + Begin the OAuth2 authorization flow. When called without a session, the user is redirected to the consent screen without grant ID. When called with a session, the redirect URL includes param for grant ID. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. + + Parameters + ---------- + client_id : Optional[str] + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. + redirect_uri : Optional[str] + Redirect URI where visitor will be redirected after authorization, whether successful or not. + response_type : Optional[str] + OAuth2 / OIDC response type. One of `code` (Authorization Code Flow), `id_token` (Implicit Flow, OIDC login only), or `code id_token` (Hybrid Flow). + scope : Optional[str] + Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`, `phone`. + state : Optional[str] + OAuth2 state. You receive this back in the redirect URI. + nonce : Optional[str] + OIDC nonce parameter to prevent replay attacks. Required when response_type includes `id_token`. + code_challenge : Optional[str] + PKCE code challenge. Required when OAuth2 app is public. + code_challenge_method : Optional[str] + PKCE code challenge method. Required when OAuth2 app is public. + prompt : Optional[str] + OIDC prompt parameter for customization of consent screen. Space-separated list of: none, login, consent, select_account. + max_age : Optional[float] + OIDC max_age paraleter for customization of consent screen. Maximum allowable elapsed time in seconds since the user last authenticated. If exceeded, re-authentication is required. + authorization_details : Optional[str] + Rich authorization request. JSON array of objects, each with a `type` and project-defined fields + resource : Optional[str] + RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. + audience : Optional[str] + Compatibility alias for a single OAuth2 resource indicator URI. + request_uri : Optional[str] + OAuth2 authorization request handle returned by the pushed authorization request endpoint. + + Returns + ------- + Oauth2Authorize + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/oauth2/{project_id}/authorize' + api_params = {} + api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) + + if client_id is not None: + api_params['client_id'] = self._normalize_value(client_id) + if redirect_uri is not None: + api_params['redirect_uri'] = self._normalize_value(redirect_uri) + if response_type is not None: + api_params['response_type'] = self._normalize_value(response_type) + if scope is not None: + api_params['scope'] = self._normalize_value(scope) + if state is not None: + api_params['state'] = self._normalize_value(state) + if nonce is not None: + api_params['nonce'] = self._normalize_value(nonce) + if code_challenge is not None: + api_params['code_challenge'] = self._normalize_value(code_challenge) + if code_challenge_method is not None: + api_params['code_challenge_method'] = self._normalize_value(code_challenge_method) + if prompt is not None: + api_params['prompt'] = self._normalize_value(prompt) + if max_age is not None: + api_params['max_age'] = self._normalize_value(max_age) + if authorization_details is not None: + api_params['authorization_details'] = self._normalize_value(authorization_details) + if resource is not None: + api_params['resource'] = self._normalize_value(resource) + if audience is not None: + api_params['audience'] = self._normalize_value(audience) + if request_uri is not None: + api_params['request_uri'] = self._normalize_value(request_uri) + + response = self.client.call('post', api_path, { + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2Authorize) + + def create_device_authorization( self, client_id: Optional[str] = None, @@ -184,7 +287,7 @@ def create_device_authorization( Parameters ---------- client_id : Optional[str] - OAuth2 client ID. + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. scope : Optional[str] Space-separated OAuth2 scopes. Can include project scopes, and built-in scopes: `openid`, `email`, `profile`. authorization_details : Optional[str] @@ -376,7 +479,7 @@ def create_par( Parameters ---------- client_id : str - OAuth2 client ID. + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. redirect_uri : str Redirect URI where visitor will be redirected after authorization, whether successful or not. response_type : str @@ -562,7 +665,7 @@ def revoke( token_type_hint : Optional[str] Type of token to revoke (access_token or refresh_token). client_id : Optional[str] - OAuth2 client ID. + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. client_secret : Optional[str] OAuth2 client secret. Required for confidential apps; omitted for public apps. @@ -627,7 +730,7 @@ def create_token( device_code : Optional[str] Device code obtained from the device authorization endpoint. Required for `urn:ietf:params:oauth:grant-type:device_code` grant type. client_id : Optional[str] - OAuth2 client ID. + OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. client_secret : Optional[str] OAuth2 client secret. Required for confidential apps. code_verifier : Optional[str] diff --git a/appwrite/services/sites.py b/appwrite/services/sites.py index 611dcb02..bcf0c1ad 100644 --- a/appwrite/services/sites.py +++ b/appwrite/services/sites.py @@ -988,7 +988,8 @@ def get_deployment_download( self, site_id: str, deployment_id: str, - type: Optional[DeploymentDownloadType] = None + type: Optional[DeploymentDownloadType] = None, + token: Optional[str] = None ) -> bytes: """ Get a site deployment content by its unique ID. The endpoint response return with a 'Content-Disposition: attachment' header that tells the browser to start downloading the file to user downloads directory. @@ -1001,6 +1002,8 @@ def get_deployment_download( Deployment ID. type : Optional[DeploymentDownloadType] Deployment file to download. Can be: "source", "output". + token : Optional[str] + Presigned source-download token for accessing this deployment without a session (jobs-service). Returns ------- @@ -1026,6 +1029,8 @@ def get_deployment_download( if type is not None: api_params['type'] = self._normalize_value(type) + if token is not None: + api_params['token'] = self._normalize_value(token) response = self.client.call('get', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), diff --git a/appwrite/services/tables_db.py b/appwrite/services/tables_db.py index 806bdc84..f84f9cca 100644 --- a/appwrite/services/tables_db.py +++ b/appwrite/services/tables_db.py @@ -5,8 +5,12 @@ from appwrite.utils.deprecated import deprecated from ..models.database_list import DatabaseList from ..models.database import Database +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList from ..models.transaction_list import TransactionList from ..models.transaction import Transaction +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.database_status import DatabaseStatus from ..models.table_list import TableList from ..models.table import Table from ..models.column_list import ColumnList @@ -96,7 +100,8 @@ def create( database_id: str, name: str, enabled: Optional[bool] = None, - specification: Optional[str] = None + specification: Optional[str] = None, + replicas: Optional[float] = None ) -> Database: """ Create a new Database. @@ -112,6 +117,8 @@ def create( Is the database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. specification : Optional[str] Database specification. Defaults to `serverless`, which creates the database on the shared pool. Any other value provisions a dedicated database on that specification. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Requires a dedicated `specification`; must be 0 for a serverless database. High availability is enabled when greater than 0. Returns ------- @@ -139,6 +146,8 @@ def create( api_params['enabled'] = self._normalize_value(enabled) if specification is not None: api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -149,6 +158,34 @@ def create( return self._parse_response(response, model=Database) + def list_specifications( + self + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/specifications' + api_params = {} + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def list_transactions( self, queries: Optional[List[str]] = None @@ -440,7 +477,8 @@ def update( self, database_id: str, name: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, + replicas: Optional[float] = None ) -> Database: """ Update a database by its unique ID. @@ -453,6 +491,8 @@ def update( Database name. Max length: 128 chars. enabled : Optional[bool] Is database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification. High availability is enabled when greater than 0. Returns ------- @@ -476,6 +516,8 @@ def update( api_params['name'] = self._normalize_value(name) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -525,6 +567,129 @@ def delete( return response + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DedicatedDatabase) + + + def get_replicas( + self, + database_id: str + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + + def get_status( + self, + database_id: str + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DatabaseStatus) + + def list_tables( self, database_id: str, diff --git a/docs/examples/account/delete-consent-token.md b/docs/examples/account/delete-consent-token.md new file mode 100644 index 00000000..614b78ee --- /dev/null +++ b/docs/examples/account/delete-consent-token.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result = account.delete_consent_token( + consent_id = '', + token_id = '' +) +``` diff --git a/docs/examples/account/delete-consent.md b/docs/examples/account/delete-consent.md new file mode 100644 index 00000000..8c2c4113 --- /dev/null +++ b/docs/examples/account/delete-consent.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result = account.delete_consent( + consent_id = '' +) +``` diff --git a/docs/examples/account/get-consent-token.md b/docs/examples/account/get-consent-token.md new file mode 100644 index 00000000..a5edd0a7 --- /dev/null +++ b/docs/examples/account/get-consent-token.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account +from appwrite.models import Oauth2ConsentToken + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result: Oauth2ConsentToken = account.get_consent_token( + consent_id = '', + token_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/account/get-consent.md b/docs/examples/account/get-consent.md new file mode 100644 index 00000000..45ba0a82 --- /dev/null +++ b/docs/examples/account/get-consent.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account +from appwrite.models import Oauth2Consent + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result: Oauth2Consent = account.get_consent( + consent_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/account/list-consent-tokens.md b/docs/examples/account/list-consent-tokens.md new file mode 100644 index 00000000..3be9fbe3 --- /dev/null +++ b/docs/examples/account/list-consent-tokens.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account +from appwrite.models import Oauth2ConsentTokenList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result: Oauth2ConsentTokenList = account.list_consent_tokens( + consent_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/account/list-consents.md b/docs/examples/account/list-consents.md new file mode 100644 index 00000000..d2b5b69c --- /dev/null +++ b/docs/examples/account/list-consents.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.account import Account +from appwrite.models import Oauth2ConsentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +account = Account(client) + +result: Oauth2ConsentList = account.list_consents( + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/list-o-auth-2-scopes.md b/docs/examples/apps/list-o-auth-2-scopes.md new file mode 100644 index 00000000..8720e78c --- /dev/null +++ b/docs/examples/apps/list-o-auth-2-scopes.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppScopeList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result: AppScopeList = apps.list_o_auth2_scopes() + +print(result.model_dump()) +``` diff --git a/docs/examples/backups/create-restoration.md b/docs/examples/backups/create-restoration.md index 03f3f0a9..e2966caa 100644 --- a/docs/examples/backups/create-restoration.md +++ b/docs/examples/backups/create-restoration.md @@ -15,8 +15,7 @@ result: BackupRestoration = backups.create_restoration( archive_id = '', services = [BackupServices.DATABASES], new_resource_id = '', # optional - new_resource_name = '', # optional - new_specification = 'serverless' # optional + new_resource_name = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/oauth2/authorize-post.md b/docs/examples/oauth2/authorize-post.md new file mode 100644 index 00000000..b6dd6449 --- /dev/null +++ b/docs/examples/oauth2/authorize-post.md @@ -0,0 +1,31 @@ +```python +from appwrite.client import Client +from appwrite.services.oauth2 import Oauth2 +from appwrite.models import Oauth2Authorize + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_session('') # The user session to authenticate with +client.set_project('') # Your project ID + +oauth2 = Oauth2(client) + +result: Oauth2Authorize = oauth2.authorize_post( + client_id = '', # optional + redirect_uri = 'https://example.com', # optional + response_type = '', # optional + scope = '', # optional + state = '', # optional + nonce = '', # optional + code_challenge = '', # optional + code_challenge_method = 's256', # optional + prompt = '', # optional + max_age = 0, # optional + authorization_details = '', # optional + resource = '', # optional + audience = '', # optional + request_uri = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/sites/get-deployment-download.md b/docs/examples/sites/get-deployment-download.md index eae2543c..7d6ae537 100644 --- a/docs/examples/sites/get-deployment-download.md +++ b/docs/examples/sites/get-deployment-download.md @@ -13,6 +13,7 @@ sites = Sites(client) result: bytes = sites.get_deployment_download( site_id = '', deployment_id = '', - type = DeploymentDownloadType.SOURCE # optional + type = DeploymentDownloadType.SOURCE, # optional + token = '' # optional ) ``` diff --git a/docs/examples/tablesdb/create-failover.md b/docs/examples/tablesdb/create-failover.md new file mode 100644 index 00000000..839f8baf --- /dev/null +++ b/docs/examples/tablesdb/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DedicatedDatabase = tables_db.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/create.md b/docs/examples/tablesdb/create.md index a816905f..0c5260cf 100644 --- a/docs/examples/tablesdb/create.md +++ b/docs/examples/tablesdb/create.md @@ -14,7 +14,8 @@ result: Database = tables_db.create( database_id = '', name = '', enabled = False, # optional - specification = 'serverless' # optional + specification = 'serverless', # optional + replicas = 0 # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/get-replicas.md b/docs/examples/tablesdb/get-replicas.md new file mode 100644 index 00000000..abd5df1b --- /dev/null +++ b/docs/examples/tablesdb/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DedicatedDatabaseReplicas = tables_db.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/get-status.md b/docs/examples/tablesdb/get-status.md new file mode 100644 index 00000000..0695da1f --- /dev/null +++ b/docs/examples/tablesdb/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DatabaseStatus = tables_db.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/list-specifications.md b/docs/examples/tablesdb/list-specifications.md new file mode 100644 index 00000000..c0fc0f8b --- /dev/null +++ b/docs/examples/tablesdb/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DedicatedDatabaseSpecificationList = tables_db.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/update.md b/docs/examples/tablesdb/update.md index aea54858..8609072e 100644 --- a/docs/examples/tablesdb/update.md +++ b/docs/examples/tablesdb/update.md @@ -13,7 +13,8 @@ tables_db = TablesDB(client) result: Database = tables_db.update( database_id = '', name = '', # optional - enabled = False # optional + enabled = False, # optional + replicas = 0 # optional ) print(result.model_dump()) diff --git a/pyproject.toml b/pyproject.toml index 10559426..0d439733 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "22.0.0" +version = "22.1.0" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" diff --git a/setup.py b/setup.py index 9557066e..1baebf1e 100644 --- a/setup.py +++ b/setup.py @@ -8,7 +8,7 @@ setuptools.setup( name = 'appwrite', packages = setuptools.find_packages(), - version = '22.0.0', + version = '22.1.0', license='BSD-3-Clause', description = 'Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', long_description = long_description, @@ -18,7 +18,7 @@ maintainer = 'Appwrite Team', maintainer_email = 'team@appwrite.io', url = 'https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/22.0.0.tar.gz', + download_url='https://github.com/appwrite/sdk-for-python/archive/22.1.0.tar.gz', install_requires=[ 'requests', 'pydantic>=2,<3', diff --git a/test/services/test_account.py b/test/services/test_account.py index 4ab80f3b..c0bab652 100644 --- a/test/services/test_account.py +++ b/test/services/test_account.py @@ -72,6 +72,108 @@ def test_create(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_consents(self, m): + data = { + "total": 5.0, + "consents": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.list_consents( + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_consent(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "expire": "2020-10-15T06:38:00.000+00:00" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.get_consent( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_consent(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.delete_consent( + '', + ) + + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_consent_tokens(self, m): + data = { + "total": 5.0, + "tokens": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.list_consent_tokens( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_consent_token(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "consentId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "expire": "2020-10-15T06:38:00.000+00:00" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.get_consent_token( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_consent_token(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.account.delete_consent_token( + '', + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_update_email(self, m): data = { diff --git a/test/services/test_activities.py b/test/services/test_activities.py index 9fcc5e4d..c4b8e550 100644 --- a/test/services/test_activities.py +++ b/test/services/test_activities.py @@ -44,10 +44,21 @@ def test_get_event(self, m): "ip": "127.0.0.1", "mode": "admin", "country": "US", + "continentCode": "NA", + "city": "Mountain View", + "subdivisions": "California", + "isp": "Google", + "autonomousSystemNumber": "15169", + "autonomousSystemOrganization": "GOOGLE", + "connectionType": "cable", + "connectionUsageType": "residential", + "connectionOrganization": "Google LLC", "time": "2020-10-15T06:38:00.000+00:00", "projectId": "610fc2f985ee0", "teamId": "610fc2f985ee0", - "hostname": "appwrite.io" + "hostname": "appwrite.io", + "sdk": "web", + "sdkVersion": "14.0.0" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_apps.py b/test/services/test_apps.py index 4520a42b..e457b572 100644 --- a/test/services/test_apps.py +++ b/test/services/test_apps.py @@ -66,6 +66,20 @@ def test_create(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_o_auth2_scopes(self, m): + data = { + "total": 5.0, + "scopes": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.list_o_auth2_scopes( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_get(self, m): data = { @@ -234,7 +248,7 @@ def test_get_secret(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "appId": "5e5ea5c16897e", - "secret": "$argon2i$v=19$m=16,t=2,p=1$MTIzMTIzMTIzMTIzMQ$3\/ZUl3IWERBO2RIm5rHltg", + "secret": "", "hint": "f5c6c7", "createdById": "5e5ea5c16897e", "createdByName": "Walter White" diff --git a/test/services/test_backups.py b/test/services/test_backups.py index dfa1f5a2..83c59835 100644 --- a/test/services/test_backups.py +++ b/test/services/test_backups.py @@ -196,7 +196,7 @@ def test_create_restoration(self, m): "migrationId": "did8jx6ws45jana098ab7", "services": [], "resources": [], - "options": "{databases.database[{oldId, newId, newName, newSpecification}]}" + "options": "{databases.database[{oldId, newId, newName}]}" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -235,7 +235,7 @@ def test_get_restoration(self, m): "migrationId": "did8jx6ws45jana098ab7", "services": [], "resources": [], - "options": "{databases.database[{oldId, newId, newName, newSpecification}]}" + "options": "{databases.database[{oldId, newId, newName}]}" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_databases.py b/test/services/test_databases.py index f6bc3112..11f4ecaf 100644 --- a/test/services/test_databases.py +++ b/test/services/test_databases.py @@ -35,9 +35,7 @@ def test_create(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -158,9 +156,7 @@ def test_get(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -179,9 +175,7 @@ def test_update(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_oauth2.py b/test/services/test_oauth2.py index 3b0bc38e..0f331808 100644 --- a/test/services/test_oauth2.py +++ b/test/services/test_oauth2.py @@ -41,6 +41,20 @@ def test_authorize(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_authorize_post(self, m): + data = { + "grantId": "5e5ea5c16897e", + "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.oauth2.authorize_post( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_create_device_authorization(self, m): data = { diff --git a/test/services/test_organization.py b/test/services/test_organization.py index 7cd67f61..399dd374 100644 --- a/test/services/test_organization.py +++ b/test/services/test_organization.py @@ -39,6 +39,7 @@ def test_get(self, m): "screenshotsGenerated": 50.0, "members": 25.0, "webhooks": 25.0, + "wafRules": 2.0, "projects": 2.0, "platforms": 3.0, "users": 25.0, @@ -264,6 +265,7 @@ def test_update(self, m): "screenshotsGenerated": 50.0, "members": 25.0, "webhooks": 25.0, + "wafRules": 2.0, "projects": 2.0, "platforms": 3.0, "users": 25.0, @@ -725,7 +727,8 @@ def test_create_project(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -766,7 +769,8 @@ def test_get_project(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -806,7 +810,8 @@ def test_update_project(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_project.py b/test/services/test_project.py index c3e87cf3..b4b9c640 100644 --- a/test/services/test_project.py +++ b/test/services/test_project.py @@ -42,7 +42,8 @@ def test_get(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -92,7 +93,8 @@ def test_update_auth_method(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -252,7 +254,8 @@ def test_update_labels(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -385,7 +388,8 @@ def test_update_o_auth2_server(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1417,7 +1421,8 @@ def test_update_deny_aliased_email_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1457,7 +1462,8 @@ def test_update_deny_corporate_email_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1497,7 +1503,8 @@ def test_update_deny_disposable_email_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1537,7 +1544,8 @@ def test_update_deny_free_email_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1577,7 +1585,8 @@ def test_update_membership_privacy_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1616,7 +1625,8 @@ def test_update_password_dictionary_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1656,7 +1666,8 @@ def test_update_password_history_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1696,7 +1707,8 @@ def test_update_password_personal_data_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1754,7 +1766,8 @@ def test_update_session_alert_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1794,7 +1807,8 @@ def test_update_session_duration_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1834,7 +1848,8 @@ def test_update_session_invalidation_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1874,7 +1889,8 @@ def test_update_session_limit_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1914,7 +1930,8 @@ def test_update_user_limit_policy(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -1969,7 +1986,8 @@ def test_update_protocol(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -2010,7 +2028,8 @@ def test_update_service(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -2051,7 +2070,8 @@ def test_update_smtp(self, m): "services": [], "protocols": [], "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00" + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) diff --git a/test/services/test_tables_db.py b/test/services/test_tables_db.py index 7f2ecabf..888be71f 100644 --- a/test/services/test_tables_db.py +++ b/test/services/test_tables_db.py @@ -35,9 +35,7 @@ def test_create(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -49,6 +47,27 @@ def test_create(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "crossRegionReplicaRate": 1, + "pitrRate": 0.2 + } +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.list_specifications( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_transactions(self, m): data = { @@ -158,9 +177,7 @@ def test_get(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -179,9 +196,7 @@ def test_update(self, m): "$createdAt": "2020-10-15T06:38:00.000+00:00", "$updatedAt": "2020-10-15T06:38:00.000+00:00", "enabled": True, - "type": "legacy", - "policies": [], - "archives": [] + "type": "legacy" } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -204,6 +219,106 @@ def test_delete(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "crossRegionReplicas": 1.0, + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.create_failover( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "members": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.get_replicas( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0 + }, + "replicas": [], + "volumes": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.get_status( + '', + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_tables(self, m): data = { From 6402b883973803040f71f50e2a4cdf1542f3e486 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Thu, 23 Jul 2026 16:17:34 +0530 Subject: [PATCH 04/10] chore: update Python SDK to 22.2.0 --- CHANGELOG.md | 9 + appwrite/client.py | 4 +- appwrite/enums/organization_key_scopes.py | 2 + appwrite/models/__init__.py | 8 + appwrite/models/app.py | 6 + appwrite/models/app_installation.py | 42 ++ appwrite/models/app_installation_list.py | 19 + appwrite/models/app_key.py | 39 ++ appwrite/models/app_key_list.py | 19 + appwrite/models/database.py | 6 + appwrite/models/project.py | 3 + appwrite/services/apps.py | 369 +++++++++++++++++- appwrite/services/organization.py | 213 ++++++++++ appwrite/services/project.py | 5 + appwrite/services/teams.py | 248 ++++++++++++ .../apps/create-installation-token.md | 19 + docs/examples/apps/create-key.md | 18 + docs/examples/apps/delete-key.md | 16 + docs/examples/apps/get-installation.md | 19 + docs/examples/apps/get-key.md | 19 + .../examples/apps/list-installation-scopes.md | 16 + docs/examples/apps/list-installations.md | 20 + docs/examples/apps/list-keys.md | 20 + docs/examples/apps/update.md | 4 +- .../organization/create-installation.md | 19 + .../organization/delete-installation.md | 15 + .../examples/organization/get-installation.md | 18 + .../organization/list-installations.md | 19 + .../organization/update-installation.md | 19 + .../project/update-o-auth-2-server.md | 1 + docs/examples/teams/create-installation.md | 20 + docs/examples/teams/delete-installation.md | 16 + docs/examples/teams/get-installation.md | 19 + docs/examples/teams/list-installations.md | 20 + docs/examples/teams/update-installation.md | 20 + pyproject.toml | 2 +- setup.py | 4 +- test/services/test_apps.py | 152 ++++++++ test/services/test_organization.py | 92 +++++ test/services/test_teams.py | 97 +++++ 40 files changed, 1669 insertions(+), 7 deletions(-) create mode 100644 appwrite/models/app_installation.py create mode 100644 appwrite/models/app_installation_list.py create mode 100644 appwrite/models/app_key.py create mode 100644 appwrite/models/app_key_list.py create mode 100644 docs/examples/apps/create-installation-token.md create mode 100644 docs/examples/apps/create-key.md create mode 100644 docs/examples/apps/delete-key.md create mode 100644 docs/examples/apps/get-installation.md create mode 100644 docs/examples/apps/get-key.md create mode 100644 docs/examples/apps/list-installation-scopes.md create mode 100644 docs/examples/apps/list-installations.md create mode 100644 docs/examples/apps/list-keys.md create mode 100644 docs/examples/organization/create-installation.md create mode 100644 docs/examples/organization/delete-installation.md create mode 100644 docs/examples/organization/get-installation.md create mode 100644 docs/examples/organization/list-installations.md create mode 100644 docs/examples/organization/update-installation.md create mode 100644 docs/examples/teams/create-installation.md create mode 100644 docs/examples/teams/delete-installation.md create mode 100644 docs/examples/teams/get-installation.md create mode 100644 docs/examples/teams/list-installations.md create mode 100644 docs/examples/teams/update-installation.md diff --git a/CHANGELOG.md b/CHANGELOG.md index d0f3fdfd..4eba1752 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,14 @@ # Change Log +## 22.2.0 + +* Added: `apps` installation and key management methods (`list_installations`, `get_installation`, `create_installation_token`, `list_installation_scopes`, `list_keys`, `create_key`, `get_key`, `delete_key`) +* Added: `installation_scopes` and `installation_redirect_url` parameters to `apps.update` +* Added: app installation management methods to `organization` and `teams` services +* Added: `installation_access_token_duration` parameter to `project.update_o_auth2_server` +* Added: `installationScopes` and `installationRedirectUrl` fields to `App` model +* Added: `organization.installations.read`/`organization.installations.write` key scopes + ## 22.1.0 * Updated: removed `new_specification` parameter from `backups.create_restoration` diff --git a/appwrite/client.py b/appwrite/client.py index 3588e3a7..6e1d40e7 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -17,11 +17,11 @@ def __init__(self): self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent' : f'AppwritePythonSDK/22.1.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent' : f'AppwritePythonSDK/22.2.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '22.1.0', + 'x-sdk-version': '22.2.0', 'X-Appwrite-Response-Format' : '1.9.5', } self._config = {} diff --git a/appwrite/enums/organization_key_scopes.py b/appwrite/enums/organization_key_scopes.py index ab4e4526..bb2515df 100644 --- a/appwrite/enums/organization_key_scopes.py +++ b/appwrite/enums/organization_key_scopes.py @@ -7,6 +7,8 @@ class OrganizationKeyScopes(Enum): DEVKEYS_WRITE = "devKeys.write" ORGANIZATION_KEYS_READ = "organization.keys.read" ORGANIZATION_KEYS_WRITE = "organization.keys.write" + ORGANIZATION_INSTALLATIONS_READ = "organization.installations.read" + ORGANIZATION_INSTALLATIONS_WRITE = "organization.installations.write" ORGANIZATION_MEMBERSHIPS_READ = "organization.memberships.read" ORGANIZATION_MEMBERSHIPS_WRITE = "organization.memberships.write" ORGANIZATION_READ = "organization.read" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 07a73030..419db211 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -243,6 +243,8 @@ from .app_secret import AppSecret from .app_secret_plaintext import AppSecretPlaintext from .app_scope import AppScope +from .app_installation import AppInstallation +from .app_key import AppKey from .oauth2_authorize import Oauth2Authorize from .oauth2_approve import Oauth2Approve from .oauth2_reject import Oauth2Reject @@ -265,6 +267,8 @@ from .apps_list import AppsList from .app_secret_list import AppSecretList from .app_scope_list import AppScopeList +from .app_installation_list import AppInstallationList +from .app_key_list import AppKeyList __all__ = [ 'AppwriteModel', @@ -512,6 +516,8 @@ 'AppSecret', 'AppSecretPlaintext', 'AppScope', + 'AppInstallation', + 'AppKey', 'Oauth2Authorize', 'Oauth2Approve', 'Oauth2Reject', @@ -534,4 +540,6 @@ 'AppsList', 'AppSecretList', 'AppScopeList', + 'AppInstallationList', + 'AppKeyList', ] diff --git a/appwrite/models/app.py b/appwrite/models/app.py index f570a66c..76e93798 100644 --- a/appwrite/models/app.py +++ b/appwrite/models/app.py @@ -56,6 +56,10 @@ class App(AppwriteModel): ID of team that owns the application, if owned by team. Otherwise, user ID will be used. userid : str ID of user who owns the application, if owned by user. Otherwise, team ID will be used. + installationscopes : List[Any] + Scopes the application requests when installed on a team. Organization-level and project-level scopes only. + installationredirecturl : str + URL users are redirected to after creating or updating an installation of this application. Empty for no redirect. secrets : List[AppSecret] List of application secrets. """ @@ -82,4 +86,6 @@ class App(AppwriteModel): deviceflow: bool = Field(..., alias='deviceFlow') teamid: str = Field(..., alias='teamId') userid: str = Field(..., alias='userId') + installationscopes: List[Any] = Field(..., alias='installationScopes') + installationredirecturl: str = Field(..., alias='installationRedirectUrl') secrets: List[AppSecret] = Field(..., alias='secrets') diff --git a/appwrite/models/app_installation.py b/appwrite/models/app_installation.py new file mode 100644 index 00000000..3984389c --- /dev/null +++ b/appwrite/models/app_installation.py @@ -0,0 +1,42 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class AppInstallation(AppwriteModel): + """ + AppInstallation + + Attributes + ---------- + id : str + Installation ID. + createdat : str + Installation creation time in ISO 8601 format. + updatedat : str + Installation update time in ISO 8601 format. + appid : str + ID of the installed application. + teamid : str + ID of the team the application is installed on. + scopes : List[Any] + Scopes granted to the application. Snapshot of the application's installation scopes taken when the installation was created or last updated. + authorizationdetails : Dict[str, Any] + Authorization details granted to the application. Rich authorization request (RFC 9396) style entries; the Appwrite Console stores authorized project IDs here. + createdbyid : str + ID of the user who created the installation. + createdbyname : str + Name of the user who created the installation. + lastaccessedat : Optional[str] + Time an access token was last issued for the installation in ISO 8601 format. Null if never used. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + appid: str = Field(..., alias='appId') + teamid: str = Field(..., alias='teamId') + scopes: List[Any] = Field(..., alias='scopes') + authorizationdetails: Dict[str, Any] = Field(..., alias='authorizationDetails') + createdbyid: str = Field(..., alias='createdById') + createdbyname: str = Field(..., alias='createdByName') + lastaccessedat: Optional[str] = Field(default=None, alias='lastAccessedAt') diff --git a/appwrite/models/app_installation_list.py b/appwrite/models/app_installation_list.py new file mode 100644 index 00000000..0519077d --- /dev/null +++ b/appwrite/models/app_installation_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .app_installation import AppInstallation + +class AppInstallationList(AppwriteModel): + """ + App installations list + + Attributes + ---------- + total : float + Total number of installations that matched your query. + installations : List[AppInstallation] + List of installations. + """ + total: float = Field(..., alias='total') + installations: List[AppInstallation] = Field(..., alias='installations') diff --git a/appwrite/models/app_key.py b/appwrite/models/app_key.py new file mode 100644 index 00000000..88a319f2 --- /dev/null +++ b/appwrite/models/app_key.py @@ -0,0 +1,39 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class AppKey(AppwriteModel): + """ + AppKey + + Attributes + ---------- + id : str + App key ID. + createdat : str + App key creation time in ISO 8601 format. + updatedat : str + App key update time in ISO 8601 format. + appid : str + Application ID this app key belongs to. + secret : str + App key secret. + hint : str + Last few characters of the app key secret, used to help identify it. + createdbyid : str + ID of the user who created the app key. + createdbyname : str + Name of the user who created the app key. + lastaccessedat : Optional[str] + Time the app key was last used for authentication in ISO 8601 format. Null if never used. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + appid: str = Field(..., alias='appId') + secret: str = Field(..., alias='secret') + hint: str = Field(..., alias='hint') + createdbyid: str = Field(..., alias='createdById') + createdbyname: str = Field(..., alias='createdByName') + lastaccessedat: Optional[str] = Field(default=None, alias='lastAccessedAt') diff --git a/appwrite/models/app_key_list.py b/appwrite/models/app_key_list.py new file mode 100644 index 00000000..2d4b7ff4 --- /dev/null +++ b/appwrite/models/app_key_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .app_key import AppKey + +class AppKeyList(AppwriteModel): + """ + App keys list + + Attributes + ---------- + total : float + Total number of keys that matched your query. + keys : List[AppKey] + List of keys. + """ + total: float = Field(..., alias='total') + keys: List[AppKey] = Field(..., alias='keys') diff --git a/appwrite/models/database.py b/appwrite/models/database.py index f83198fd..c1852901 100644 --- a/appwrite/models/database.py +++ b/appwrite/models/database.py @@ -27,6 +27,10 @@ class Database(AppwriteModel): Database type. status : Optional[DatabaseStatus] Dedicated database lifecycle status. Null when the database has no valid dedicated backing. + engine : Optional[str] + Underlying engine of the dedicated backing: postgresql, mysql, mariadb, or mongodb. A managed product (tablesdb, documentsdb, vectorsdb) reports the engine it runs on, so its type and engine can differ. Null when the database has no dedicated backing. + specification : Optional[str] + Compute specification identifier of the dedicated backing, e.g. s-2vcpu-2gb. Null when the database has no dedicated backing. replicas : Optional[float] Number of secondary high availability replicas, excluding the primary. Null when backing configuration is unavailable. policies : Optional[List[BackupPolicy]] @@ -41,6 +45,8 @@ class Database(AppwriteModel): enabled: bool = Field(..., alias='enabled') type: DatabaseType = Field(..., alias='type') status: Optional[DatabaseStatus] = Field(default=None, alias='status') + engine: Optional[str] = Field(default=None, alias='engine') + specification: Optional[str] = Field(default=None, alias='specification') replicas: Optional[float] = Field(default=None, alias='replicas') policies: Optional[List[BackupPolicy]] = Field(default=None, alias='policies') archives: Optional[List[BackupArchive]] = Field(default=None, alias='archives') diff --git a/appwrite/models/project.py b/appwrite/models/project.py index 3dd2ca01..76822354 100644 --- a/appwrite/models/project.py +++ b/appwrite/models/project.py @@ -91,6 +91,8 @@ class Project(AppwriteModel): OAuth2 server access token duration in seconds for public clients (SPAs, mobile, native) oauth2serverpublicrefreshtokenduration : Optional[float] OAuth2 server refresh token duration in seconds for public clients (SPAs, mobile, native) + oauth2serverinstallationaccesstokenduration : Optional[float] + OAuth2 server access token duration in seconds for app installation access tokens oauth2serverconfidentialpkce : Optional[bool] When enabled, PKCE is required for confidential clients (server-side flows using client_secret). PKCE is always required for public clients regardless of this setting. oauth2serververificationurl : Optional[str] @@ -142,6 +144,7 @@ class Project(AppwriteModel): oauth2serverrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerRefreshTokenDuration') oauth2serverpublicaccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerPublicAccessTokenDuration') oauth2serverpublicrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerPublicRefreshTokenDuration') + oauth2serverinstallationaccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerInstallationAccessTokenDuration') oauth2serverconfidentialpkce: Optional[bool] = Field(default=None, alias='oAuth2ServerConfidentialPkce') oauth2serververificationurl: Optional[str] = Field(default=None, alias='oAuth2ServerVerificationUrl') oauth2serverusercodelength: Optional[float] = Field(default=None, alias='oAuth2ServerUserCodeLength') diff --git a/appwrite/services/apps.py b/appwrite/services/apps.py index 8b8e3285..d4a3f681 100644 --- a/appwrite/services/apps.py +++ b/appwrite/services/apps.py @@ -6,6 +6,11 @@ from ..models.apps_list import AppsList from ..models.app import App from ..models.app_scope_list import AppScopeList +from ..models.app_installation_list import AppInstallationList +from ..models.app_installation import AppInstallation +from ..models.oauth2_token import Oauth2Token +from ..models.app_key_list import AppKeyList +from ..models.app_key import AppKey from ..models.app_secret_list import AppSecretList from ..models.app_secret_plaintext import AppSecretPlaintext from ..models.app_secret import AppSecret @@ -191,6 +196,34 @@ def create( return self._parse_response(response, model=App) + def list_installation_scopes( + self + ) -> AppScopeList: + """ + List scopes an application can request when installed on a team. + + Returns + ------- + AppScopeList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/scopes/installations' + api_params = {} + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppScopeList) + + def list_o_auth2_scopes( self ) -> AppScopeList: @@ -277,7 +310,9 @@ def update( redirect_uris: Optional[List[str]] = None, post_logout_redirect_uris: Optional[List[str]] = None, type: Optional[str] = None, - device_flow: Optional[bool] = None + device_flow: Optional[bool] = None, + installation_scopes: Optional[List[str]] = None, + installation_redirect_url: Optional[str] = None ) -> App: """ Update an application by its unique ID. @@ -320,6 +355,10 @@ def update( OAuth2 client type. Use `public` for SPAs, mobile, and native apps that cannot keep a `client_secret` — PKCE is then required at the token endpoint. Use `confidential` for server-side clients that present a `client_secret`. Defaults to `confidential`. device_flow : Optional[bool] Allow this client to use the OAuth2 Device Authorization Grant (RFC 8628) for input-constrained devices such as TVs and CLIs. Defaults to false. + installation_scopes : Optional[List[str]] + Scopes the application requests when installed on a team. Organization-level and project-level scopes only; use the list scopes endpoint with `type=installation` to discover available values. Maximum of 100 scopes are allowed. + installation_redirect_url : Optional[str] + URL users are redirected to after creating or updating an installation of this application. Must be an https URL, an http loopback URL (localhost, 127.0.0.1, [::1]), or a private-use scheme URI, and must not contain a fragment. Leave empty for no redirect. Returns ------- @@ -375,6 +414,10 @@ def update( api_params['type'] = self._normalize_value(type) if device_flow is not None: api_params['deviceFlow'] = self._normalize_value(device_flow) + if installation_scopes is not None: + api_params['installationScopes'] = self._normalize_value(installation_scopes) + if installation_redirect_url is not None: + api_params['installationRedirectUrl'] = self._normalize_value(installation_redirect_url) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -425,6 +468,330 @@ def delete( return response + def list_installations( + self, + app_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> AppInstallationList: + """ + List installations of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. + + Parameters + ---------- + app_id : str + Application unique ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + AppInstallationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/installations' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallationList) + + + def get_installation( + self, + app_id: str, + installation_id: str + ) -> AppInstallation: + """ + Get an installation of an application by its unique ID. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. + + Parameters + ---------- + app_id : str + Application unique ID. + installation_id : str + Installation unique ID. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/installations/{installationId}' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def create_installation_token( + self, + app_id: str, + installation_id: str + ) -> Oauth2Token: + """ + Create a token for an installation of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. The returned token carries the scopes and authorization details granted to the installation, and can be used as an `Authorization: Bearer` header everywhere OAuth2 access tokens are accepted. Multiple tokens can be active for the same installation at once; each token stays valid until it expires or the installation is updated or deleted. + + Parameters + ---------- + app_id : str + Application unique ID. + installation_id : str + Installation unique ID. + + Returns + ------- + Oauth2Token + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/installations/{installationId}/tokens' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=Oauth2Token) + + + def list_keys( + self, + app_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> AppKeyList: + """ + List app keys for an application. + + Parameters + ---------- + app_id : str + Application unique ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + AppKeyList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/keys' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppKeyList) + + + def create_key( + self, + app_id: str + ) -> AppKey: + """ + Create a new app key for an application. App keys carry no scopes; send one in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header to list the application's installations and create installation access tokens. + + Parameters + ---------- + app_id : str + Application unique ID. + + Returns + ------- + AppKey + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/keys' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppKey) + + + def get_key( + self, + app_id: str, + key_id: str + ) -> AppKey: + """ + Get an app key by its unique ID. + + Parameters + ---------- + app_id : str + Application unique ID. + key_id : str + App key unique ID. + + Returns + ------- + AppKey + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/keys/{keyId}' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if key_id is None: + raise AppwriteException('Missing required parameter: "key_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppKey) + + + def delete_key( + self, + app_id: str, + key_id: str + ) -> Dict[str, Any]: + """ + Delete an app key by its unique ID. + + Parameters + ---------- + app_id : str + Application unique ID. + key_id : str + App key unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/keys/{keyId}' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if key_id is None: + raise AppwriteException('Missing required parameter: "key_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + def update_labels( self, app_id: str, diff --git a/appwrite/services/organization.py b/appwrite/services/organization.py index e3f11e50..6ea8aa89 100644 --- a/appwrite/services/organization.py +++ b/appwrite/services/organization.py @@ -4,6 +4,8 @@ from ..exception import AppwriteException from appwrite.utils.deprecated import deprecated from ..models.organization import Organization as OrganizationModel +from ..models.app_installation_list import AppInstallationList +from ..models.app_installation import AppInstallation from ..models.key_list import KeyList from ..enums.organization_key_scopes import OrganizationKeyScopes from ..models.key import Key @@ -127,6 +129,217 @@ def delete( return response + def list_installations( + self, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> AppInstallationList: + """ + List app installations on the organization. Any organization member can read installations. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + AppInstallationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/installations' + api_params = {} + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallationList) + + + def create_installation( + self, + app_id: str, + authorization_details: Optional[str] = None + ) -> AppInstallation: + """ + Install an app on the organization. Only organization members with the owner role can install apps. The installation is granted the scopes the app currently requests. + + Parameters + ---------- + app_id : str + Application unique ID. + authorization_details : Optional[str] + Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. The Appwrite Console stores authorized project IDs here. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/installations' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + + api_params['appId'] = self._normalize_value(app_id) + if authorization_details is not None: + api_params['authorizationDetails'] = self._normalize_value(authorization_details) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def get_installation( + self, + installation_id: str + ) -> AppInstallation: + """ + Get an app installation on the organization by its unique ID. Any organization member can read installations. + + Parameters + ---------- + installation_id : str + Installation unique ID. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/installations/{installationId}' + api_params = {} + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def update_installation( + self, + installation_id: str, + authorization_details: Optional[str] = None + ) -> AppInstallation: + """ + Update an app installation on the organization. Only organization members with the owner role can update installations. The installation's granted scopes are refreshed to the scopes the app currently requests; previously issued installation access tokens are revoked. + + Parameters + ---------- + installation_id : str + Installation unique ID. + authorization_details : Optional[str] + Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. Omit to keep the current value. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/installations/{installationId}' + api_params = {} + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + if authorization_details is not None: + api_params['authorizationDetails'] = self._normalize_value(authorization_details) + + response = self.client.call('put', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def delete_installation( + self, + installation_id: str + ) -> Dict[str, Any]: + """ + Uninstall an app from the organization by its installation ID. Only organization members with the owner role can remove installations. Previously issued installation access tokens are revoked. + + Parameters + ---------- + installation_id : str + Installation unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/organization/installations/{installationId}' + api_params = {} + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + def list_keys( self, queries: Optional[List[str]] = None, diff --git a/appwrite/services/project.py b/appwrite/services/project.py index 573abdae..38af962f 100644 --- a/appwrite/services/project.py +++ b/appwrite/services/project.py @@ -790,6 +790,7 @@ def update_o_auth2_server( refresh_token_duration: Optional[float] = None, public_access_token_duration: Optional[float] = None, public_refresh_token_duration: Optional[float] = None, + installation_access_token_duration: Optional[float] = None, confidential_pkce: Optional[bool] = None, verification_url: Optional[str] = None, user_code_length: Optional[float] = None, @@ -818,6 +819,8 @@ def update_o_auth2_server( Access token duration in seconds for public clients (SPAs, mobile, and native apps that cannot keep a client secret). Leave empty to use default 1 hour. public_refresh_token_duration : Optional[float] Refresh token duration in seconds for public clients (SPAs, mobile, and native apps that cannot keep a client secret). Leave empty to use default 30 days. + installation_access_token_duration : Optional[float] + Access token duration in seconds for app installation access tokens. Leave empty to use default 1 hour. confidential_pkce : Optional[bool] When enabled, PKCE is required for confidential clients (server-side flows using client_secret). PKCE is always required for public clients regardless of this setting. verification_url : Optional[str] @@ -865,6 +868,8 @@ def update_o_auth2_server( api_params['publicAccessTokenDuration'] = self._normalize_value(public_access_token_duration) if public_refresh_token_duration is not None: api_params['publicRefreshTokenDuration'] = self._normalize_value(public_refresh_token_duration) + if installation_access_token_duration is not None: + api_params['installationAccessTokenDuration'] = self._normalize_value(installation_access_token_duration) if confidential_pkce is not None: api_params['confidentialPkce'] = self._normalize_value(confidential_pkce) if verification_url is not None: diff --git a/appwrite/services/teams.py b/appwrite/services/teams.py index 6b8a6fc9..45594204 100644 --- a/appwrite/services/teams.py +++ b/appwrite/services/teams.py @@ -5,6 +5,8 @@ from appwrite.utils.deprecated import deprecated from ..models.team_list import TeamList from ..models.team import Team +from ..models.app_installation_list import AppInstallationList +from ..models.app_installation import AppInstallation from ..models.membership_list import MembershipList from ..models.membership import Membership from ..models.preferences import Preferences @@ -256,6 +258,252 @@ def delete( return response + def list_installations( + self, + team_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None + ) -> AppInstallationList: + """ + List app installations on a team. Any team member can read installations. + + Parameters + ---------- + team_id : str + Team ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + + Returns + ------- + AppInstallationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/teams/{teamId}/installations' + api_params = {} + if team_id is None: + raise AppwriteException('Missing required parameter: "team_id"') + + api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) + + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallationList) + + + def create_installation( + self, + team_id: str, + app_id: str, + authorization_details: Optional[str] = None + ) -> AppInstallation: + """ + Install an app on a team. When authenticated as a user, only team members with the owner role can install apps. Requests using an API key or in admin mode can install apps on any team. The installation is granted the scopes the app currently requests. + + Parameters + ---------- + team_id : str + Team ID. + app_id : str + Application unique ID. + authorization_details : Optional[str] + Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. The Appwrite Console stores authorized project IDs here. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/teams/{teamId}/installations' + api_params = {} + if team_id is None: + raise AppwriteException('Missing required parameter: "team_id"') + + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) + + api_params['appId'] = self._normalize_value(app_id) + if authorization_details is not None: + api_params['authorizationDetails'] = self._normalize_value(authorization_details) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def get_installation( + self, + team_id: str, + installation_id: str + ) -> AppInstallation: + """ + Get an app installation on a team by its unique ID. Any team member can read installations. + + Parameters + ---------- + team_id : str + Team ID. + installation_id : str + Installation unique ID. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/teams/{teamId}/installations/{installationId}' + api_params = {} + if team_id is None: + raise AppwriteException('Missing required parameter: "team_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def update_installation( + self, + team_id: str, + installation_id: str, + authorization_details: Optional[str] = None + ) -> AppInstallation: + """ + Update an app installation on a team. Only team members with the owner role can update installations. The installation's granted scopes are refreshed to the scopes the app currently requests; previously issued installation access tokens are revoked. + + Parameters + ---------- + team_id : str + Team ID. + installation_id : str + Installation unique ID. + authorization_details : Optional[str] + Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. Omit to keep the current value. + + Returns + ------- + AppInstallation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/teams/{teamId}/installations/{installationId}' + api_params = {} + if team_id is None: + raise AppwriteException('Missing required parameter: "team_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + if authorization_details is not None: + api_params['authorizationDetails'] = self._normalize_value(authorization_details) + + response = self.client.call('put', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=AppInstallation) + + + def delete_installation( + self, + team_id: str, + installation_id: str + ) -> Dict[str, Any]: + """ + Uninstall an app from a team by its installation ID. Only team members with the owner role can remove installations. Previously issued installation access tokens are revoked. + + Parameters + ---------- + team_id : str + Team ID. + installation_id : str + Installation unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/teams/{teamId}/installations/{installationId}' + api_params = {} + if team_id is None: + raise AppwriteException('Missing required parameter: "team_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + def list_memberships( self, team_id: str, diff --git a/docs/examples/apps/create-installation-token.md b/docs/examples/apps/create-installation-token.md new file mode 100644 index 00000000..62a62ca6 --- /dev/null +++ b/docs/examples/apps/create-installation-token.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import Oauth2Token + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +apps = Apps(client) + +result: Oauth2Token = apps.create_installation_token( + app_id = '', + installation_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/create-key.md b/docs/examples/apps/create-key.md new file mode 100644 index 00000000..2821ba65 --- /dev/null +++ b/docs/examples/apps/create-key.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppKey + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result: AppKey = apps.create_key( + app_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/delete-key.md b/docs/examples/apps/delete-key.md new file mode 100644 index 00000000..dca52e39 --- /dev/null +++ b/docs/examples/apps/delete-key.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result = apps.delete_key( + app_id = '', + key_id = '' +) +``` diff --git a/docs/examples/apps/get-installation.md b/docs/examples/apps/get-installation.md new file mode 100644 index 00000000..f6a52721 --- /dev/null +++ b/docs/examples/apps/get-installation.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +apps = Apps(client) + +result: AppInstallation = apps.get_installation( + app_id = '', + installation_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/get-key.md b/docs/examples/apps/get-key.md new file mode 100644 index 00000000..4df3d424 --- /dev/null +++ b/docs/examples/apps/get-key.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppKey + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result: AppKey = apps.get_key( + app_id = '', + key_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/list-installation-scopes.md b/docs/examples/apps/list-installation-scopes.md new file mode 100644 index 00000000..4705cf7b --- /dev/null +++ b/docs/examples/apps/list-installation-scopes.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppScopeList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result: AppScopeList = apps.list_installation_scopes() + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/list-installations.md b/docs/examples/apps/list-installations.md new file mode 100644 index 00000000..f5e292b2 --- /dev/null +++ b/docs/examples/apps/list-installations.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppInstallationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +apps = Apps(client) + +result: AppInstallationList = apps.list_installations( + app_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/list-keys.md b/docs/examples/apps/list-keys.md new file mode 100644 index 00000000..7ed78543 --- /dev/null +++ b/docs/examples/apps/list-keys.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.apps import Apps +from appwrite.models import AppKeyList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +apps = Apps(client) + +result: AppKeyList = apps.list_keys( + app_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/apps/update.md b/docs/examples/apps/update.md index 49c85efb..c9006df6 100644 --- a/docs/examples/apps/update.md +++ b/docs/examples/apps/update.md @@ -28,7 +28,9 @@ result: App = apps.update( redirect_uris = [], # optional post_logout_redirect_uris = [], # optional type = 'public', # optional - device_flow = False # optional + device_flow = False, # optional + installation_scopes = [], # optional + installation_redirect_url = 'https://example.com' # optional ) print(result.model_dump()) diff --git a/docs/examples/organization/create-installation.md b/docs/examples/organization/create-installation.md new file mode 100644 index 00000000..c7af602a --- /dev/null +++ b/docs/examples/organization/create-installation.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +organization = Organization(client) + +result: AppInstallation = organization.create_installation( + app_id = '', + authorization_details = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/organization/delete-installation.md b/docs/examples/organization/delete-installation.md new file mode 100644 index 00000000..82790282 --- /dev/null +++ b/docs/examples/organization/delete-installation.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +organization = Organization(client) + +result = organization.delete_installation( + installation_id = '' +) +``` diff --git a/docs/examples/organization/get-installation.md b/docs/examples/organization/get-installation.md new file mode 100644 index 00000000..0bd78a30 --- /dev/null +++ b/docs/examples/organization/get-installation.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +organization = Organization(client) + +result: AppInstallation = organization.get_installation( + installation_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/organization/list-installations.md b/docs/examples/organization/list-installations.md new file mode 100644 index 00000000..c2ebe4e8 --- /dev/null +++ b/docs/examples/organization/list-installations.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization +from appwrite.models import AppInstallationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +organization = Organization(client) + +result: AppInstallationList = organization.list_installations( + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/organization/update-installation.md b/docs/examples/organization/update-installation.md new file mode 100644 index 00000000..ab8301b2 --- /dev/null +++ b/docs/examples/organization/update-installation.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.organization import Organization +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +organization = Organization(client) + +result: AppInstallation = organization.update_installation( + installation_id = '', + authorization_details = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/project/update-o-auth-2-server.md b/docs/examples/project/update-o-auth-2-server.md index 6be24c54..bce0876e 100644 --- a/docs/examples/project/update-o-auth-2-server.md +++ b/docs/examples/project/update-o-auth-2-server.md @@ -19,6 +19,7 @@ result: ProjectModel = project.update_o_auth2_server( refresh_token_duration = 60, # optional public_access_token_duration = 60, # optional public_refresh_token_duration = 60, # optional + installation_access_token_duration = 60, # optional confidential_pkce = False, # optional verification_url = 'https://example.com', # optional user_code_length = 6, # optional diff --git a/docs/examples/teams/create-installation.md b/docs/examples/teams/create-installation.md new file mode 100644 index 00000000..185e379f --- /dev/null +++ b/docs/examples/teams/create-installation.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.teams import Teams +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +teams = Teams(client) + +result: AppInstallation = teams.create_installation( + team_id = '', + app_id = '', + authorization_details = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/teams/delete-installation.md b/docs/examples/teams/delete-installation.md new file mode 100644 index 00000000..912195d3 --- /dev/null +++ b/docs/examples/teams/delete-installation.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.teams import Teams + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +teams = Teams(client) + +result = teams.delete_installation( + team_id = '', + installation_id = '' +) +``` diff --git a/docs/examples/teams/get-installation.md b/docs/examples/teams/get-installation.md new file mode 100644 index 00000000..06ad5f01 --- /dev/null +++ b/docs/examples/teams/get-installation.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.teams import Teams +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +teams = Teams(client) + +result: AppInstallation = teams.get_installation( + team_id = '', + installation_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/teams/list-installations.md b/docs/examples/teams/list-installations.md new file mode 100644 index 00000000..fbc9485b --- /dev/null +++ b/docs/examples/teams/list-installations.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.teams import Teams +from appwrite.models import AppInstallationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +teams = Teams(client) + +result: AppInstallationList = teams.list_installations( + team_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/teams/update-installation.md b/docs/examples/teams/update-installation.md new file mode 100644 index 00000000..a5df1213 --- /dev/null +++ b/docs/examples/teams/update-installation.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.teams import Teams +from appwrite.models import AppInstallation + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +teams = Teams(client) + +result: AppInstallation = teams.update_installation( + team_id = '', + installation_id = '', + authorization_details = '' # optional +) + +print(result.model_dump()) +``` diff --git a/pyproject.toml b/pyproject.toml index 0d439733..b71d5337 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "22.1.0" +version = "22.2.0" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" diff --git a/setup.py b/setup.py index 1baebf1e..3d51ebff 100644 --- a/setup.py +++ b/setup.py @@ -8,7 +8,7 @@ setuptools.setup( name = 'appwrite', packages = setuptools.find_packages(), - version = '22.1.0', + version = '22.2.0', license='BSD-3-Clause', description = 'Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', long_description = long_description, @@ -18,7 +18,7 @@ maintainer = 'Appwrite Team', maintainer_email = 'team@appwrite.io', url = 'https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/22.1.0.tar.gz', + download_url='https://github.com/appwrite/sdk-for-python/archive/22.2.0.tar.gz', install_requires=[ 'requests', 'pydantic>=2,<3', diff --git a/test/services/test_apps.py b/test/services/test_apps.py index e457b572..e923f2e5 100644 --- a/test/services/test_apps.py +++ b/test/services/test_apps.py @@ -53,6 +53,8 @@ def test_create(self, m): "deviceFlow": True, "teamId": "5e5ea5c16897e", "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", "secrets": [] } headers = {'Content-Type': 'application/json'} @@ -66,6 +68,20 @@ def test_create(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_installation_scopes(self, m): + data = { + "total": 5.0, + "scopes": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.list_installation_scopes( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_o_auth2_scopes(self, m): data = { @@ -106,6 +122,8 @@ def test_get(self, m): "deviceFlow": True, "teamId": "5e5ea5c16897e", "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", "secrets": [] } headers = {'Content-Type': 'application/json'} @@ -143,6 +161,8 @@ def test_update(self, m): "deviceFlow": True, "teamId": "5e5ea5c16897e", "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", "secrets": [] } headers = {'Content-Type': 'application/json'} @@ -167,6 +187,134 @@ def test_delete(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_list_installations(self, m): + data = { + "total": 5.0, + "installations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.list_installations( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.get_installation( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_installation_token(self, m): + data = { + "access_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9...", + "token_type": "Bearer", + "expires_in": 3600.0, + "refresh_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...", + "scope": "openid email profile" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.create_installation_token( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_keys(self, m): + data = { + "total": 5.0, + "keys": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.list_keys( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_key(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.create_key( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_key(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.get_key( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_key(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.delete_key( + '', + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_update_labels(self, m): data = { @@ -193,6 +341,8 @@ def test_update_labels(self, m): "deviceFlow": True, "teamId": "5e5ea5c16897e", "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", "secrets": [] } headers = {'Content-Type': 'application/json'} @@ -302,6 +452,8 @@ def test_update_team(self, m): "deviceFlow": True, "teamId": "5e5ea5c16897e", "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", "secrets": [] } headers = {'Content-Type': 'application/json'} diff --git a/test/services/test_organization.py b/test/services/test_organization.py index 399dd374..544d647d 100644 --- a/test/services/test_organization.py +++ b/test/services/test_organization.py @@ -477,6 +477,98 @@ def test_delete(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_list_installations(self, m): + data = { + "total": 5.0, + "installations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.list_installations( + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.create_installation( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.get_installation( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.update_installation( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_installation(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.organization.delete_installation( + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_list_keys(self, m): data = { diff --git a/test/services/test_teams.py b/test/services/test_teams.py index 84688663..684d00f8 100644 --- a/test/services/test_teams.py +++ b/test/services/test_teams.py @@ -98,6 +98,103 @@ def test_delete(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_list_installations(self, m): + data = { + "total": 5.0, + "installations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.teams.list_installations( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.teams.create_installation( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.teams.get_installation( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_installation(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": {}, + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.teams.update_installation( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_installation(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.teams.delete_installation( + '', + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_list_memberships(self, m): data = { From 253f92583fa46b13199b11fc92a5b7334b6f2216 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Thu, 23 Jul 2026 17:01:53 +0530 Subject: [PATCH 05/10] chore: update Python SDK to 22.2.0 --- .github/workflows/publish.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index f0e30cb5..53679c3b 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -9,10 +9,10 @@ jobs: runs-on: ubuntu-latest steps: - name: Check out code - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 - name: Set up Python - uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0 + uses: actions/setup-python@5fda3b95a4ea91299a34e894583c3862153e4b97 # v7.0.0 with: python-version: '3.9' From a29b3154708246695c691952362cb1691762cecb Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 14 Aug 2026 13:41:48 +0530 Subject: [PATCH 06/10] chore: update Python SDK to 23.0.0 --- .github/workflows/publish.yml | 22 +- CHANGELOG.md | 18 + README.md | 2 +- appwrite/client.py | 13 +- appwrite/encoders/value_class_encoder.py | 8 + appwrite/enums/authentication_factor.py | 1 + appwrite/enums/build_runtime.py | 1 + appwrite/enums/embedding_model.py | 7 + appwrite/enums/invalidation_type.py | 6 + appwrite/enums/project_key_scopes.py | 2 + appwrite/enums/project_policy_id.py | 1 + appwrite/enums/runtime.py | 1 + appwrite/models/__init__.py | 18 + appwrite/models/billing_plan.py | 16 +- appwrite/models/billing_plan_addon.py | 8 +- appwrite/models/billing_plan_addon_details.py | 4 +- appwrite/models/database.py | 2 +- appwrite/models/database_migration.py | 60 ++++ appwrite/models/database_migration_list.py | 19 ++ appwrite/models/database_status.py | 24 +- .../models/database_status_connections.py | 2 +- appwrite/models/database_status_replica.py | 4 +- appwrite/models/dedicated_database.py | 9 +- appwrite/models/dedicated_database_member.py | 10 +- .../models/dedicated_database_operation.py | 45 +++ .../dedicated_database_operation_list.py | 19 ++ .../models/dedicated_database_replicas.py | 17 +- ...edicated_database_specification_pricing.py | 3 - appwrite/models/document.py | 81 +++-- appwrite/models/document_list.py | 2 +- appwrite/models/embedding.py | 24 ++ appwrite/models/embedding_list.py | 19 ++ appwrite/models/file.py | 6 + appwrite/models/mfa_challenge_secret.py | 27 ++ appwrite/models/mfa_factors.py | 3 + appwrite/models/organization.py | 50 +-- appwrite/models/policy_list.py | 5 +- appwrite/models/policy_mfa_factors.py | 27 ++ appwrite/models/preferences.py | 59 ++-- appwrite/models/project.py | 3 + appwrite/models/proxy_invalidation.py | 24 ++ appwrite/models/row.py | 81 +++-- appwrite/models/row_list.py | 2 +- appwrite/models/team_list.py | 2 +- appwrite/models/usage_billing_plan.py | 12 +- appwrite/models/user_list.py | 2 +- appwrite/service.py | 3 +- appwrite/services/account.py | 41 +-- appwrite/services/activities.py | 4 +- appwrite/services/apps.py | 57 +++- appwrite/services/backups.py | 6 +- appwrite/services/databases.py | 8 +- appwrite/services/embeddings.py | 58 ++++ appwrite/services/functions.py | 2 +- appwrite/services/project.py | 148 ++++---- appwrite/services/proxy.py | 56 ++++ appwrite/services/sites.py | 2 +- appwrite/services/storage.py | 7 +- appwrite/services/tables_db.py | 317 +++++++++++++++++- appwrite/services/users.py | 47 +++ docs/examples/activities/list-events.md | 2 +- .../apps/create-installation-token.md | 2 +- .../delete-installation.md} | 12 +- docs/examples/apps/get-installation.md | 2 +- docs/examples/apps/list-installations.md | 2 +- .../embeddings/create-text-embeddings.md | 20 ++ docs/examples/project/get-policy.md | 3 +- ...te-key.md => update-mfa-factors-policy.md} | 13 +- .../project/update-o-auth-2-server.md | 3 +- .../project/update-session-duration-policy.md | 2 +- .../project/update-user-limit-policy.md | 2 +- docs/examples/proxy/create-invalidation.md | 21 ++ docs/examples/storage/create-file.md | 3 +- docs/examples/tablesdb/create-migration.md | 20 ++ docs/examples/tablesdb/create.md | 3 +- docs/examples/tablesdb/cutover-migration.md | 19 ++ docs/examples/tablesdb/delete-migration.md | 16 + docs/examples/tablesdb/get-migration.md | 19 ++ docs/examples/tablesdb/list-migrations.md | 18 + docs/examples/tablesdb/list-operations.md | 21 ++ docs/examples/tablesdb/update.md | 4 +- docs/examples/users/get-mfa-challenge.md | 19 ++ pyproject.toml | 2 +- setup.py | 4 +- test/services/test_account.py | 20 +- test/services/test_apps.py | 13 + test/services/test_embeddings.py | 30 ++ test/services/test_organization.py | 126 +------ test/services/test_project.py | 64 ++-- test/services/test_proxy.py | 18 + test/services/test_storage.py | 6 + test/services/test_tables_db.py | 142 +++++++- test/services/test_teams.py | 2 - test/services/test_users.py | 27 +- 94 files changed, 1724 insertions(+), 483 deletions(-) create mode 100644 appwrite/enums/embedding_model.py create mode 100644 appwrite/enums/invalidation_type.py create mode 100644 appwrite/models/database_migration.py create mode 100644 appwrite/models/database_migration_list.py create mode 100644 appwrite/models/dedicated_database_operation.py create mode 100644 appwrite/models/dedicated_database_operation_list.py create mode 100644 appwrite/models/embedding.py create mode 100644 appwrite/models/embedding_list.py create mode 100644 appwrite/models/mfa_challenge_secret.py create mode 100644 appwrite/models/policy_mfa_factors.py create mode 100644 appwrite/models/proxy_invalidation.py create mode 100644 appwrite/services/embeddings.py rename docs/examples/{account/create-jwt.md => apps/delete-installation.md} (58%) create mode 100644 docs/examples/embeddings/create-text-embeddings.md rename docs/examples/project/{create-key.md => update-mfa-factors-policy.md} (58%) create mode 100644 docs/examples/proxy/create-invalidation.md create mode 100644 docs/examples/tablesdb/create-migration.md create mode 100644 docs/examples/tablesdb/cutover-migration.md create mode 100644 docs/examples/tablesdb/delete-migration.md create mode 100644 docs/examples/tablesdb/get-migration.md create mode 100644 docs/examples/tablesdb/list-migrations.md create mode 100644 docs/examples/tablesdb/list-operations.md create mode 100644 docs/examples/users/get-mfa-challenge.md create mode 100644 test/services/test_embeddings.py diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 53679c3b..dfbf4972 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -2,14 +2,28 @@ name: Publish to PyPI on: release: types: [published] + workflow_dispatch: + inputs: + tag: + description: 'Release tag to publish, e.g. 1.2.3' + required: true jobs: publish: name: Release build and publish runs-on: ubuntu-latest + permissions: + # Mints the short-lived OIDC token PyPI exchanges for an upload token, so + # no long-lived API token has to be stored on the repository. + id-token: write steps: - name: Check out code uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 + with: + # A release build must come from the tag, never from a branch that may + # have moved on. On a release event github.ref is already the tag; on a + # manual retry the tag has to be named explicitly. + ref: ${{ inputs.tag || github.ref }} - name: Set up Python uses: actions/setup-python@5fda3b95a4ea91299a34e894583c3862153e4b97 # v7.0.0 @@ -22,10 +36,4 @@ jobs: python setup.py sdist bdist_wheel - name: Publish package - run: | - python -m pip install twine - python -m twine upload -r pypi dist/* - env: - TWINE_USERNAME: __token__ - TWINE_PASSWORD: ${{ secrets.PYPI_TOKEN }} - TWINE_NON_INTERACTIVE: true + uses: pypa/gh-action-pypi-publish@dc37677b2e1c63e2034f94d8a5b11f265b73ba33 # v1.14.2 diff --git a/CHANGELOG.md b/CHANGELOG.md index 4eba1752..52fb6a98 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,23 @@ # Change Log +## 23.0.0 + +* Breaking: removed `account.createJWT`; use `users.createJWT` instead. A leaked JWT could mint further JWTs, letting a credential outlive its own expiry — a session cannot duplicate itself to live forever either +* Breaking: removed `project.createKey`. A leaked key could mint further hidden keys, making a compromise far harder to contain and revoke +* Breaking: `activities.listEvents` `queries` now takes an array instead of a string +* Added: `embeddings` service with `createTextEmbeddings`, plus the `EmbeddingModel` enum +* Added: TablesDB migration methods `listMigrations`, `createMigration`, `getMigration`, `deleteMigration`, `cutoverMigration`, and `listOperations` +* Added: `proxy.createInvalidation` for purging cached edge responses, plus the `InvalidationType` enum +* Added: `apps.deleteInstallation` +* Added: `users.getMFAChallenge` and the `MfaChallengeSecret` model +* Added: `project.updateMFAFactorsPolicy` and the `PolicyMfaFactors` model +* Added: `client.setOrganization` for organization-scoped requests +* Added: `folder` parameter to `storage.createFile` +* Added: `syncMode` parameter to `tablesDB.create` and `tablesDB.update`, and `specification` to `tablesDB.update` +* Added: `installationScopes` parameter to `project.updateOAuth2Server` +* Added: `custom` authentication factor, `node-26` runtime, `mfa-factors` project policy, and the `embeddings.write` and `proxy.invalidations.write` key scopes +* Updated: response format to `1.9.6` + ## 22.2.0 * Added: `apps` installation and key management methods (`list_installations`, `get_installation`, `create_installation_token`, `list_installation_scopes`, `list_keys`, `create_key`, `get_key`, `delete_key`) diff --git a/README.md b/README.md index 60a89373..926d11a4 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Appwrite Python SDK ![License](https://img.shields.io/github/license/appwrite/sdk-for-python.svg?style=flat-square) -![Version](https://img.shields.io/badge/api%20version-1.9.5-blue.svg?style=flat-square) +![Version](https://img.shields.io/badge/api%20version-1.9.6-blue.svg?style=flat-square) [![Build Status](https://img.shields.io/travis/com/appwrite/sdk-generator?style=flat-square)](https://travis-ci.com/appwrite/sdk-generator) [![Twitter Account](https://img.shields.io/twitter/follow/appwrite?color=00acee&label=twitter&style=flat-square)](https://twitter.com/appwrite) [![Discord](https://img.shields.io/discord/564160730845151244?label=discord&style=flat-square)](https://appwrite.io/discord) diff --git a/appwrite/client.py b/appwrite/client.py index 6e1d40e7..67ba5631 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -17,12 +17,12 @@ def __init__(self): self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent' : f'AppwritePythonSDK/22.2.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent' : f'AppwritePythonSDK/23.0.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '22.2.0', - 'X-Appwrite-Response-Format' : '1.9.5', + 'x-sdk-version': '23.0.0', + 'X-Appwrite-Response-Format' : '1.9.6', } self._config = {} @@ -60,6 +60,13 @@ def set_key(self, value): self._config['key'] = value return self + def set_organization(self, value): + """Your organization ID""" + + self._global_headers['x-appwrite-organization'] = value + self._config['organization'] = value + return self + def set_jwt(self, value): """Your secret JSON Web Token""" diff --git a/appwrite/encoders/value_class_encoder.py b/appwrite/encoders/value_class_encoder.py index b725fb9b..ab46a105 100644 --- a/appwrite/encoders/value_class_encoder.py +++ b/appwrite/encoders/value_class_encoder.py @@ -15,6 +15,7 @@ from ..enums.relation_mutate import RelationMutate from ..enums.databases_index_type import DatabasesIndexType from ..enums.order_by import OrderBy +from ..enums.embedding_model import EmbeddingModel from ..enums.runtime import Runtime from ..enums.project_key_scopes import ProjectKeyScopes from ..enums.template_reference_type import TemplateReferenceType @@ -35,6 +36,7 @@ from ..enums.project_smtp_secure import ProjectSMTPSecure from ..enums.project_email_template_id import ProjectEmailTemplateId from ..enums.project_email_template_locale import ProjectEmailTemplateLocale +from ..enums.invalidation_type import InvalidationType from ..enums.status_code import StatusCode from ..enums.proxy_resource_type import ProxyResourceType from ..enums.framework import Framework @@ -111,6 +113,9 @@ def default(self, o): if isinstance(o, OrderBy): return o.value + if isinstance(o, EmbeddingModel): + return o.value + if isinstance(o, Runtime): return o.value @@ -171,6 +176,9 @@ def default(self, o): if isinstance(o, ProjectEmailTemplateLocale): return o.value + if isinstance(o, InvalidationType): + return o.value + if isinstance(o, StatusCode): return o.value diff --git a/appwrite/enums/authentication_factor.py b/appwrite/enums/authentication_factor.py index a5b8cf2a..9e1f1add 100644 --- a/appwrite/enums/authentication_factor.py +++ b/appwrite/enums/authentication_factor.py @@ -5,3 +5,4 @@ class AuthenticationFactor(Enum): PHONE = "phone" TOTP = "totp" RECOVERYCODE = "recoverycode" + CUSTOM = "custom" diff --git a/appwrite/enums/build_runtime.py b/appwrite/enums/build_runtime.py index 7b1c6dc1..8472bd82 100644 --- a/appwrite/enums/build_runtime.py +++ b/appwrite/enums/build_runtime.py @@ -11,6 +11,7 @@ class BuildRuntime(Enum): NODE_23 = "node-23" NODE_24 = "node-24" NODE_25 = "node-25" + NODE_26 = "node-26" PHP_8_0 = "php-8.0" PHP_8_1 = "php-8.1" PHP_8_2 = "php-8.2" diff --git a/appwrite/enums/embedding_model.py b/appwrite/enums/embedding_model.py new file mode 100644 index 00000000..5bbf1cf9 --- /dev/null +++ b/appwrite/enums/embedding_model.py @@ -0,0 +1,7 @@ +from enum import Enum + +class EmbeddingModel(Enum): + NOMIC_EMBED_TEXT = "nomic-embed-text" + EMBEDDING_GEMMA = "embedding-gemma" + ALL_MINILM = "all-minilm" + BGE_SMALL = "bge-small" diff --git a/appwrite/enums/invalidation_type.py b/appwrite/enums/invalidation_type.py new file mode 100644 index 00000000..1a8f7707 --- /dev/null +++ b/appwrite/enums/invalidation_type.py @@ -0,0 +1,6 @@ +from enum import Enum + +class InvalidationType(Enum): + TAG = "tag" + PATH = "path" + ALL = "all" diff --git a/appwrite/enums/project_key_scopes.py b/appwrite/enums/project_key_scopes.py index e29a2454..d96ff939 100644 --- a/appwrite/enums/project_key_scopes.py +++ b/appwrite/enums/project_key_scopes.py @@ -35,6 +35,7 @@ class ProjectKeyScopes(Enum): INDEXES_WRITE = "indexes.write" ROWS_READ = "rows.read" ROWS_WRITE = "rows.write" + EMBEDDINGS_WRITE = "embeddings.write" COLLECTIONS_READ = "collections.read" COLLECTIONS_WRITE = "collections.write" ATTRIBUTES_READ = "attributes.read" @@ -99,6 +100,7 @@ class ProjectKeyScopes(Enum): WAFRULES_READ = "wafRules.read" WAFRULES_WRITE = "wafRules.write" EVENTS_READ = "events.read" + PROXY_INVALIDATIONS_WRITE = "proxy.invalidations.write" APPS_READ = "apps.read" APPS_WRITE = "apps.write" OAUTH2_READ = "oauth2.read" diff --git a/appwrite/enums/project_policy_id.py b/appwrite/enums/project_policy_id.py index 56ca022b..02b97a3e 100644 --- a/appwrite/enums/project_policy_id.py +++ b/appwrite/enums/project_policy_id.py @@ -11,6 +11,7 @@ class ProjectPolicyId(Enum): SESSION_LIMIT = "session-limit" USER_LIMIT = "user-limit" MEMBERSHIP_PRIVACY = "membership-privacy" + MFA_FACTORS = "mfa-factors" DENY_ALIASED_EMAIL = "deny-aliased-email" DENY_DISPOSABLE_EMAIL = "deny-disposable-email" DENY_FREE_EMAIL = "deny-free-email" diff --git a/appwrite/enums/runtime.py b/appwrite/enums/runtime.py index 74e3a279..0bc261ca 100644 --- a/appwrite/enums/runtime.py +++ b/appwrite/enums/runtime.py @@ -11,6 +11,7 @@ class Runtime(Enum): NODE_23 = "node-23" NODE_24 = "node-24" NODE_25 = "node-25" + NODE_26 = "node-26" PHP_8_0 = "php-8.0" PHP_8_1 = "php-8.1" PHP_8_2 = "php-8.2" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 419db211..9b7d0ced 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -43,9 +43,11 @@ from .target_list import TargetList from .transaction_list import TransactionList from .specification_list import SpecificationList +from .embedding_list import EmbeddingList from .insight_list import InsightList from .report_list import ReportList from .database import Database +from .embedding import Embedding from .collection import Collection from .attribute_list import AttributeList from .attribute_string import AttributeString @@ -180,6 +182,7 @@ from .policy_session_limit import PolicySessionLimit from .policy_user_limit import PolicyUserLimit from .policy_membership_privacy import PolicyMembershipPrivacy +from .policy_mfa_factors import PolicyMfaFactors from .platform_web import PlatformWeb from .platform_apple import PlatformApple from .platform_android import PlatformAndroid @@ -197,6 +200,7 @@ from .proxy_rule import ProxyRule from .email_template import EmailTemplate from .mfa_challenge import MfaChallenge +from .mfa_challenge_secret import MfaChallengeSecret from .mfa_recovery_codes import MfaRecoveryCodes from .mfa_type import MfaType from .mfa_factors import MfaFactors @@ -220,10 +224,14 @@ from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits from .billing_plan_supported_addons import BillingPlanSupportedAddons from .block import Block +from .database_migration import DatabaseMigration from .dedicated_database import DedicatedDatabase from .database_status import DatabaseStatus from .dedicated_database_member import DedicatedDatabaseMember +from .dedicated_database_operation import DedicatedDatabaseOperation +from .dedicated_database_operation_list import DedicatedDatabaseOperationList from .dedicated_database_replicas import DedicatedDatabaseReplicas +from .proxy_invalidation import ProxyInvalidation from .organization import Organization from .backup_policy import BackupPolicy from .policy_deny_aliased_email import PolicyDenyAliasedEmail @@ -264,6 +272,7 @@ from .backup_archive_list import BackupArchiveList from .backup_policy_list import BackupPolicyList from .backup_restoration_list import BackupRestorationList +from .database_migration_list import DatabaseMigrationList from .apps_list import AppsList from .app_secret_list import AppSecretList from .app_scope_list import AppScopeList @@ -316,9 +325,11 @@ 'TargetList', 'TransactionList', 'SpecificationList', + 'EmbeddingList', 'InsightList', 'ReportList', 'Database', + 'Embedding', 'Collection', 'AttributeList', 'AttributeString', @@ -453,6 +464,7 @@ 'PolicySessionLimit', 'PolicyUserLimit', 'PolicyMembershipPrivacy', + 'PolicyMfaFactors', 'PlatformWeb', 'PlatformApple', 'PlatformAndroid', @@ -470,6 +482,7 @@ 'ProxyRule', 'EmailTemplate', 'MfaChallenge', + 'MfaChallengeSecret', 'MfaRecoveryCodes', 'MfaType', 'MfaFactors', @@ -493,10 +506,14 @@ 'BillingPlanDedicatedDatabaseLimits', 'BillingPlanSupportedAddons', 'Block', + 'DatabaseMigration', 'DedicatedDatabase', 'DatabaseStatus', 'DedicatedDatabaseMember', + 'DedicatedDatabaseOperation', + 'DedicatedDatabaseOperationList', 'DedicatedDatabaseReplicas', + 'ProxyInvalidation', 'Organization', 'BackupPolicy', 'PolicyDenyAliasedEmail', @@ -537,6 +554,7 @@ 'BackupArchiveList', 'BackupPolicyList', 'BackupRestorationList', + 'DatabaseMigrationList', 'AppsList', 'AppSecretList', 'AppScopeList', diff --git a/appwrite/models/billing_plan.py b/appwrite/models/billing_plan.py index c37db9d3..dfe4d167 100644 --- a/appwrite/models/billing_plan.py +++ b/appwrite/models/billing_plan.py @@ -36,7 +36,7 @@ class BillingPlan(AppwriteModel): Image Transformations screenshotsgenerated : float Screenshots generated - members : float + members : Optional[float] Members webhooks : float Webhooks @@ -84,7 +84,7 @@ class BillingPlan(AppwriteModel): SMS authentications per month domains : float Custom domains - activitylogs : float + activitylogs : Optional[float] Activity log days usagelogs : float Usage history days @@ -132,13 +132,13 @@ class BillingPlan(AppwriteModel): Does plan support restricting sign-ups to corporate email addresses only. supportsprojectspecificroles : bool Does plan support project-specific member roles. - backupsenabled : bool + backupsenabled : Optional[bool] Does plan support backup policies. usageperproject : bool Whether usage addons are calculated per project. supportedaddons : BillingPlanSupportedAddons Supported addons for this plan - backuppolicies : float + backuppolicies : Optional[float] How many policies does plan support deploymentsize : float Maximum function and site deployment size in MB @@ -165,7 +165,7 @@ class BillingPlan(AppwriteModel): storage: float = Field(..., alias='storage') imagetransformations: float = Field(..., alias='imageTransformations') screenshotsgenerated: float = Field(..., alias='screenshotsGenerated') - members: float = Field(..., alias='members') + members: Optional[float] = Field(default=None, alias='members') webhooks: float = Field(..., alias='webhooks') wafrules: float = Field(..., alias='wafRules') projects: float = Field(..., alias='projects') @@ -189,7 +189,7 @@ class BillingPlan(AppwriteModel): topics: float = Field(..., alias='topics') authphone: float = Field(..., alias='authPhone') domains: float = Field(..., alias='domains') - activitylogs: float = Field(..., alias='activityLogs') + activitylogs: Optional[float] = Field(default=None, alias='activityLogs') usagelogs: float = Field(..., alias='usageLogs') usagelogsintervals: Optional[List[Any]] = Field(default=None, alias='usageLogsIntervals') projectinactivitydays: float = Field(..., alias='projectInactivityDays') @@ -213,10 +213,10 @@ class BillingPlan(AppwriteModel): supportsfreeemailvalidation: bool = Field(..., alias='supportsFreeEmailValidation') supportscorporateemailvalidation: bool = Field(..., alias='supportsCorporateEmailValidation') supportsprojectspecificroles: bool = Field(..., alias='supportsProjectSpecificRoles') - backupsenabled: bool = Field(..., alias='backupsEnabled') + backupsenabled: Optional[bool] = Field(default=None, alias='backupsEnabled') usageperproject: bool = Field(..., alias='usagePerProject') supportedaddons: BillingPlanSupportedAddons = Field(..., alias='supportedAddons') - backuppolicies: float = Field(..., alias='backupPolicies') + backuppolicies: Optional[float] = Field(default=None, alias='backupPolicies') deploymentsize: float = Field(..., alias='deploymentSize') buildsize: float = Field(..., alias='buildSize') databasesallowencrypt: bool = Field(..., alias='databasesAllowEncrypt') diff --git a/appwrite/models/billing_plan_addon.py b/appwrite/models/billing_plan_addon.py index b1d75b34..6ad96a36 100644 --- a/appwrite/models/billing_plan_addon.py +++ b/appwrite/models/billing_plan_addon.py @@ -10,10 +10,10 @@ class BillingPlanAddon(AppwriteModel): Attributes ---------- - seats : BillingPlanAddonDetails + seats : Optional[BillingPlanAddonDetails] Addon seats - projects : BillingPlanAddonDetails + projects : Optional[BillingPlanAddonDetails] Addon projects """ - seats: BillingPlanAddonDetails = Field(..., alias='seats') - projects: BillingPlanAddonDetails = Field(..., alias='projects') + seats: Optional[BillingPlanAddonDetails] = Field(default=None, alias='seats') + projects: Optional[BillingPlanAddonDetails] = Field(default=None, alias='projects') diff --git a/appwrite/models/billing_plan_addon_details.py b/appwrite/models/billing_plan_addon_details.py index 8acd360c..67b2754a 100644 --- a/appwrite/models/billing_plan_addon_details.py +++ b/appwrite/models/billing_plan_addon_details.py @@ -17,7 +17,7 @@ class BillingPlanAddonDetails(AppwriteModel): Addon limit type : str Addon type - currency : str + currency : Optional[str] Price currency price : float Price @@ -30,7 +30,7 @@ class BillingPlanAddonDetails(AppwriteModel): planincluded: float = Field(..., alias='planIncluded') limit: float = Field(..., alias='limit') type: str = Field(..., alias='type') - currency: str = Field(..., alias='currency') + currency: Optional[str] = Field(default=None, alias='currency') price: float = Field(..., alias='price') value: float = Field(..., alias='value') invoicedesc: str = Field(..., alias='invoiceDesc') diff --git a/appwrite/models/database.py b/appwrite/models/database.py index c1852901..6c02040a 100644 --- a/appwrite/models/database.py +++ b/appwrite/models/database.py @@ -28,7 +28,7 @@ class Database(AppwriteModel): status : Optional[DatabaseStatus] Dedicated database lifecycle status. Null when the database has no valid dedicated backing. engine : Optional[str] - Underlying engine of the dedicated backing: postgresql, mysql, mariadb, or mongodb. A managed product (tablesdb, documentsdb, vectorsdb) reports the engine it runs on, so its type and engine can differ. Null when the database has no dedicated backing. + Underlying engine of the dedicated backing: postgresql, mysql, or mongodb. A managed product (tablesdb, documentsdb, vectorsdb) reports the engine it runs on, so its type and engine can differ. Null when the database has no dedicated backing. specification : Optional[str] Compute specification identifier of the dedicated backing, e.g. s-2vcpu-2gb. Null when the database has no dedicated backing. replicas : Optional[float] diff --git a/appwrite/models/database_migration.py b/appwrite/models/database_migration.py new file mode 100644 index 00000000..f1bcea3b --- /dev/null +++ b/appwrite/models/database_migration.py @@ -0,0 +1,60 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DatabaseMigration(AppwriteModel): + """ + Database Migration + + Attributes + ---------- + id : str + Database migration ID. + createdat : str + Migration creation time in ISO 8601 format. + updatedat : str + Migration update time in ISO 8601 format. + projectid : str + Project ID that owns the migrating database. + databaseid : str + Logical database ID being migrated. + specification : str + Dedicated compute specification provisioned for the migration target. + phase : str + Migration phase. Possible values: pending, provisioned, capturing, backfilling, catching_up, verifying, ready_to_cutover, cutover, soaking, done, failed, rolled_back. + attempt : float + Number of times a migration step has failed and been recorded. + lasterror : str + Reason the most recent migration step failed, empty while none has. + lagdocuments : float + Number of documents still pending replication to the target. + verifiedat : str + Time the migrated data was verified against the source in ISO 8601 format. + cutoverat : str + Time routing was flipped to the target in ISO 8601 format. + soakuntil : str + Time the post-cutover soak window ends in ISO 8601 format. + autocutover : bool + Whether the migration cuts over automatically once ready. Set when the migration is created and never changed afterwards, so it always reports what was asked for. + cutoverrequested : bool + Whether a cutover has been requested and not yet attempted. Set by the cutover endpoint and cleared when the attempt is made, so a cutover that fails a check parks the migration again rather than retrying on its own. + paused : bool + Whether the migration is paused. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + projectid: str = Field(..., alias='projectId') + databaseid: str = Field(..., alias='databaseId') + specification: str = Field(..., alias='specification') + phase: str = Field(..., alias='phase') + attempt: float = Field(..., alias='attempt') + lasterror: str = Field(..., alias='lastError') + lagdocuments: float = Field(..., alias='lagDocuments') + verifiedat: str = Field(..., alias='verifiedAt') + cutoverat: str = Field(..., alias='cutoverAt') + soakuntil: str = Field(..., alias='soakUntil') + autocutover: bool = Field(..., alias='autoCutover') + cutoverrequested: bool = Field(..., alias='cutoverRequested') + paused: bool = Field(..., alias='paused') diff --git a/appwrite/models/database_migration_list.py b/appwrite/models/database_migration_list.py new file mode 100644 index 00000000..63571efb --- /dev/null +++ b/appwrite/models/database_migration_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .database_migration import DatabaseMigration + +class DatabaseMigrationList(AppwriteModel): + """ + Database Migrations List + + Attributes + ---------- + total : float + Total number of migrations that matched your query. + migrations : List[DatabaseMigration] + List of migrations. + """ + total: float = Field(..., alias='total') + migrations: List[DatabaseMigration] = Field(..., alias='migrations') diff --git a/appwrite/models/database_status.py b/appwrite/models/database_status.py index dd469917..34d3c1f6 100644 --- a/appwrite/models/database_status.py +++ b/appwrite/models/database_status.py @@ -13,19 +13,31 @@ class DatabaseStatus(AppwriteModel): Attributes ---------- health : str - Overall health status: healthy, degraded, or unhealthy. + Overall health status: healthy, degraded, unhealthy, or unknown when nothing could be measured. ready : bool Whether the database is ready to accept connections. engine : str - Database engine: postgresql, mysql, mariadb, or mongodb. + Database engine: postgresql, mysql, or mongodb. version : str Database engine version. uptime : float Database uptime in seconds. connections : DatabaseStatusConnections Connection statistics. + syncmode : str + Requested replication sync mode. Possible values: async, sync, quorum. Compare with effectiveSyncMode for what the primary is enforcing. + effectivesyncmode : Optional[str] + Replication sync mode the primary is actually enforcing. Null when high availability is disabled or the state could not be read. + syncdegraded : bool + Whether the enforced replication is weaker than the requested syncMode. + syncacknowledgements : float + Number of standby acknowledgements the primary waits for before a write is committed. + syncstandbycount : float + Number of standbys registered with the primary for synchronous replication. + syncstateconfirmed : Optional[bool] + Whether the other sync fields are an engine reading rather than a recorded estimate. True when the primary answered what it is enforcing, including when that answer contradicted the record, in which case the contradicted values are replaced by the ones the engine reports. False when the reading could not be taken: the probe did not answer, there was no engine to ask, or the values describe a configuration change just applied rather than anything measured. Absent when no engine was asked at all, so an unprobed database is distinguishable from an unconfirmed one. False never means a standby was found lagging, because it is the absence of a reading rather than a negative one, so draw no conclusion about replication health from it or from a response that omits it. replicas : List[DatabaseStatusReplica] - List of database replicas and their status. + List of database replicas and their status. Every configured member appears, including one the backend has not brought up, which is reported as not healthy. volumes : List[DatabaseStatusVolume] Storage volume information. """ @@ -35,5 +47,11 @@ class DatabaseStatus(AppwriteModel): version: str = Field(..., alias='version') uptime: float = Field(..., alias='uptime') connections: DatabaseStatusConnections = Field(..., alias='connections') + syncmode: str = Field(..., alias='syncMode') + effectivesyncmode: Optional[str] = Field(default=None, alias='effectiveSyncMode') + syncdegraded: bool = Field(..., alias='syncDegraded') + syncacknowledgements: float = Field(..., alias='syncAcknowledgements') + syncstandbycount: float = Field(..., alias='syncStandbyCount') + syncstateconfirmed: Optional[bool] = Field(default=None, alias='syncStateConfirmed') replicas: List[DatabaseStatusReplica] = Field(..., alias='replicas') volumes: List[DatabaseStatusVolume] = Field(..., alias='volumes') diff --git a/appwrite/models/database_status_connections.py b/appwrite/models/database_status_connections.py index fe335596..6cfa52e2 100644 --- a/appwrite/models/database_status_connections.py +++ b/appwrite/models/database_status_connections.py @@ -12,7 +12,7 @@ class DatabaseStatusConnections(AppwriteModel): current : float Current number of active connections. max : float - Maximum allowed connections. + The engine's own max_connections. On a pooled database this is the backend limit the pooler multiplexes onto, not the ceiling a client pool may reach — that is networkMaxConnections on the database resource. """ current: float = Field(..., alias='current') max: float = Field(..., alias='max') diff --git a/appwrite/models/database_status_replica.py b/appwrite/models/database_status_replica.py index 73cf79e4..91428e91 100644 --- a/appwrite/models/database_status_replica.py +++ b/appwrite/models/database_status_replica.py @@ -10,9 +10,9 @@ class DatabaseStatusReplica(AppwriteModel): Attributes ---------- index : float - StatefulSet pod index (0 = primary, 1+ = replicas). + Member index within the database. Read `role` for which member accepts writes: a failover moves the primary without renumbering the indexes. role : str - Replica role: primary or replica. + Member role. Possible values: primary (accepts reads and writes), replica (read-only follower), unknown (placement not established; reported while a transition is moving or restarting the topology, so no member can be named the write target). healthy : bool Whether the replica is healthy. lagseconds : Optional[float] diff --git a/appwrite/models/dedicated_database.py b/appwrite/models/dedicated_database.py index 9f943228..810fe7df 100644 --- a/appwrite/models/dedicated_database.py +++ b/appwrite/models/dedicated_database.py @@ -22,7 +22,7 @@ class DedicatedDatabase(AppwriteModel): api : str Product API that owns this database: tablesdb, documentsdb, vectorsdb, mysql, postgresql, or mongodb. engine : str - Database engine: postgresql, mysql, mariadb, or mongodb. + Database engine: postgresql, mysql, or mongodb. Null until the backing reports one. version : str Database engine version. specification : str @@ -32,7 +32,7 @@ class DedicatedDatabase(AppwriteModel): hostname : str Database hostname for connections. connectionport : float - Database port for connections. + Database port for connections. Derived from the engine when the backing has not reported one yet. connectionuser : str Database username for connections. connectionpassword : str @@ -69,10 +69,8 @@ class DedicatedDatabase(AppwriteModel): Number of high availability replicas. High availability is enabled when greater than 0. syncmode : str Replication sync mode: async, sync, or quorum. - crossregionreplicas : float - Number of cross-region replicas. Cross-region availability is enabled when greater than 0. networkmaxconnections : float - Maximum concurrent connections. + Maximum concurrent client connections. This is the limit a client pool may reach; the engine's own max_connections reported by the status endpoint is a smaller backend limit the pooler multiplexes onto and does not constrain a client pool. networkidletimeoutseconds : float Connection idle timeout in seconds. networkipallowlist : List[Any] @@ -138,7 +136,6 @@ class DedicatedDatabase(AppwriteModel): nodepool: str = Field(..., alias='nodePool') replicas: float = Field(..., alias='replicas') syncmode: str = Field(..., alias='syncMode') - crossregionreplicas: float = Field(..., alias='crossRegionReplicas') networkmaxconnections: float = Field(..., alias='networkMaxConnections') networkidletimeoutseconds: float = Field(..., alias='networkIdleTimeoutSeconds') networkipallowlist: List[Any] = Field(..., alias='networkIPAllowlist') diff --git a/appwrite/models/dedicated_database_member.py b/appwrite/models/dedicated_database_member.py index 6cb4daa3..128021bb 100644 --- a/appwrite/models/dedicated_database_member.py +++ b/appwrite/models/dedicated_database_member.py @@ -12,13 +12,13 @@ class DedicatedDatabaseMember(AppwriteModel): id : str Member identifier. role : str - Member role. Possible values: primary (accepts reads and writes), replica (read-only follower). + Member role. Possible values: primary (accepts reads and writes), replica (read-only follower), unknown (placement not established; reported while a transition is moving or restarting the topology and this member has not been probed, so no member can be named the write target). status : str - Member pod status. Possible values: provisioning (pod missing or Pending), starting (Running but not Ready), active (Running and Ready), failed (Failed phase or CrashLoopBackOff container), or the lowercased pod phase reported by the cluster. - lagseconds : float - Replication lag in seconds. + Member pod status. Possible values: pending (configured but absent from the backend topology, so nothing is bringing it up), provisioning (pod missing or Pending), starting (Running but not Ready), active (Running and Ready), failed (Failed phase or CrashLoopBackOff container), or the lowercased pod phase reported by the cluster. + lagseconds : Optional[float] + Replication lag in seconds. Null when the lag is not known: a primary has none to report, and a member the backend has not probed has none yet. """ id: str = Field(..., alias='$id') role: str = Field(..., alias='role') status: str = Field(..., alias='status') - lagseconds: float = Field(..., alias='lagSeconds') + lagseconds: Optional[float] = Field(default=None, alias='lagSeconds') diff --git a/appwrite/models/dedicated_database_operation.py b/appwrite/models/dedicated_database_operation.py new file mode 100644 index 00000000..97d482d3 --- /dev/null +++ b/appwrite/models/dedicated_database_operation.py @@ -0,0 +1,45 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class DedicatedDatabaseOperation(AppwriteModel): + """ + Operation + + Attributes + ---------- + id : str + Operation ID. + createdat : str + Operation creation time in ISO 8601 format. + databaseid : str + Database ID the operation ran against. + type : str + Operation type, such as provision, update, restore, pausing, resuming, failover, backup-create or cross-region-enable. + status : str + Operation status. Possible values: running (in progress), completed (finished successfully), failed (ended in an error). + attempts : float + Number of times this operation has been attempted. + requestedat : Optional[str] + Time the operation was requested, in ISO 8601 format. + startedat : Optional[str] + Time the operation started, in ISO 8601 format. + completedat : Optional[str] + Time the operation reached a terminal state, in ISO 8601 format. + errorcode : str + Machine-readable failure code. `Interrupted` marks an attempt that ended before its outcome could be confirmed. + errormessage : str + Failure message if the operation failed. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + databaseid: str = Field(..., alias='databaseId') + type: str = Field(..., alias='type') + status: str = Field(..., alias='status') + attempts: float = Field(..., alias='attempts') + requestedat: Optional[str] = Field(default=None, alias='requestedAt') + startedat: Optional[str] = Field(default=None, alias='startedAt') + completedat: Optional[str] = Field(default=None, alias='completedAt') + errorcode: str = Field(..., alias='errorCode') + errormessage: str = Field(..., alias='errorMessage') diff --git a/appwrite/models/dedicated_database_operation_list.py b/appwrite/models/dedicated_database_operation_list.py new file mode 100644 index 00000000..012e21d5 --- /dev/null +++ b/appwrite/models/dedicated_database_operation_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_operation import DedicatedDatabaseOperation + +class DedicatedDatabaseOperationList(AppwriteModel): + """ + OperationList + + Attributes + ---------- + total : float + Total number of operations. + operations : List[DedicatedDatabaseOperation] + List of operations. + """ + total: float = Field(..., alias='total') + operations: List[DedicatedDatabaseOperation] = Field(..., alias='operations') diff --git a/appwrite/models/dedicated_database_replicas.py b/appwrite/models/dedicated_database_replicas.py index fa19a87a..45e6de40 100644 --- a/appwrite/models/dedicated_database_replicas.py +++ b/appwrite/models/dedicated_database_replicas.py @@ -13,10 +13,25 @@ class DedicatedDatabaseReplicas(AppwriteModel): replicas : float Number of configured replicas. Zero means high availability is disabled. syncmode : str - Replication sync mode. Possible values: async (asynchronous, fastest), sync (synchronous, strong consistency), quorum (quorum-based, majority of replicas must confirm). + Requested replication sync mode. Possible values: async (asynchronous, fastest), sync (synchronous, strong consistency), quorum (quorum-based, majority of replicas must confirm). This is what was asked for; compare it with effectiveSyncMode for what the primary is enforcing. + effectivesyncmode : Optional[str] + Replication sync mode the primary is actually enforcing. Null when high availability is disabled or the state could not be read. A value below the requested syncMode means writes are being acknowledged with weaker durability than configured. + syncdegraded : bool + Whether the enforced replication is weaker than the requested syncMode. + syncacknowledgements : float + Number of standby acknowledgements the primary waits for before a write is committed. Zero means writes are acknowledged locally. + syncstandbycount : float + Number of standbys registered with the primary for synchronous replication. + syncstateconfirmed : Optional[bool] + Whether the other sync fields are an engine reading rather than a recorded estimate. True when the primary answered what it is enforcing, including when that answer contradicted the record, in which case the contradicted values are replaced by the ones the engine reports. False when the reading could not be taken: the probe did not answer, there was no engine to ask, or the values describe a configuration change just applied rather than anything measured. Absent when no engine was asked at all, so an unprobed database is distinguishable from an unconfirmed one. False never means a standby was found lagging, because it is the absence of a reading rather than a negative one, so draw no conclusion about replication health from it or from a response that omits it. members : List[DedicatedDatabaseMember] Per-pod statuses for the primary and every replica. """ replicas: float = Field(..., alias='replicas') syncmode: str = Field(..., alias='syncMode') + effectivesyncmode: Optional[str] = Field(default=None, alias='effectiveSyncMode') + syncdegraded: bool = Field(..., alias='syncDegraded') + syncacknowledgements: float = Field(..., alias='syncAcknowledgements') + syncstandbycount: float = Field(..., alias='syncStandbyCount') + syncstateconfirmed: Optional[bool] = Field(default=None, alias='syncStateConfirmed') members: List[DedicatedDatabaseMember] = Field(..., alias='members') diff --git a/appwrite/models/dedicated_database_specification_pricing.py b/appwrite/models/dedicated_database_specification_pricing.py index 43d3b1e7..4c614a5a 100644 --- a/appwrite/models/dedicated_database_specification_pricing.py +++ b/appwrite/models/dedicated_database_specification_pricing.py @@ -15,13 +15,10 @@ class DedicatedDatabaseSpecificationPricing(AppwriteModel): Price per GB of bandwidth above the included amount, per month, in USD. replicarate : float High availability replica price as a fraction of the specification cost. - crossregionreplicarate : float - Cross-region replica price as a fraction of the specification cost. pitrrate : float Point-in-time recovery price as a fraction of the specification cost. """ storageoveragerate: float = Field(..., alias='storageOverageRate') bandwidthoveragerate: float = Field(..., alias='bandwidthOverageRate') replicarate: float = Field(..., alias='replicaRate') - crossregionreplicarate: float = Field(..., alias='crossRegionReplicaRate') pitrrate: float = Field(..., alias='pitrRate') diff --git a/appwrite/models/document.py b/appwrite/models/document.py index 4df880fc..b0ae18f4 100644 --- a/appwrite/models/document.py +++ b/appwrite/models/document.py @@ -1,10 +1,12 @@ from typing import Any, Dict, List, Optional, Union, cast, Generic, TypeVar, Type -from pydantic import Field, PrivateAttr +from pydantic import Field, PrivateAttr, TypeAdapter, model_serializer from .base_model import AppwriteModel T = TypeVar('T') +_PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Document(AppwriteModel, Generic[T]): """ Document @@ -57,24 +59,63 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) - def model_dump(self, **kwargs) -> Dict[str, Any]: - result = super().model_dump(**kwargs) - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(**kwargs) - else: - result['data'] = self._data - return result + def _serialize_data(self, info, include=None, exclude=None): + if hasattr(self._data, 'model_dump'): + return self._data.model_dump( + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + if isinstance(self._data, dict) and (include is not None or exclude is not None): + return _PAYLOAD_ADAPTER.dump_python( + self._data, + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + return self._data + + @staticmethod + def _select_data(selector): + """ + Resolves a pydantic include/exclude selector against the 'data' key, which is + serialized here rather than declared as a field. Returns whether the key was + named, and any nested selector to apply within it. + """ + if selector is None: + return False, None + + if isinstance(selector, dict): + if 'data' not in selector: + return False, None + + nested = selector['data'] + + return True, nested if isinstance(nested, (dict, set, frozenset, list, tuple)) else None + + return 'data' in selector, None + + @model_serializer(mode='wrap') + def _serialize_model(self, handler, info): + result = handler(self) + included, include_fields = self._select_data(info.include) + excluded, exclude_fields = self._select_data(info.exclude) + + if info.include is not None and not included: + return result + + if excluded and exclude_fields is None: + return result - def to_dict(self) -> Dict[str, Any]: - result = super().to_dict() - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(mode='json') - else: - result['data'] = self._data + result['data'] = self._serialize_data(info, include_fields, exclude_fields) return result diff --git a/appwrite/models/document_list.py b/appwrite/models/document_list.py index a73bb75c..728c8039 100644 --- a/appwrite/models/document_list.py +++ b/appwrite/models/document_list.py @@ -26,7 +26,7 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Documen instance = cls.model_validate(data) if 'documents' in data and data['documents'] is not None: instance.documents = [ - Document.with_data(row, model_type) + Document.with_data(row, model_type) for row in data['documents'] ] return instance diff --git a/appwrite/models/embedding.py b/appwrite/models/embedding.py new file mode 100644 index 00000000..9da9bab5 --- /dev/null +++ b/appwrite/models/embedding.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Embedding(AppwriteModel): + """ + Embedding + + Attributes + ---------- + model : str + Embedding model used to generate embeddings. + dimension : float + Number of dimensions for each embedding vector. + embedding : List[Any] + Embedding vector values. If an error occurs, this will be an empty array. + error : str + Error message if embedding generation fails. Empty string if no error. + """ + model: str = Field(..., alias='model') + dimension: float = Field(..., alias='dimension') + embedding: List[Any] = Field(..., alias='embedding') + error: str = Field(..., alias='error') diff --git a/appwrite/models/embedding_list.py b/appwrite/models/embedding_list.py new file mode 100644 index 00000000..d8f437e7 --- /dev/null +++ b/appwrite/models/embedding_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .embedding import Embedding + +class EmbeddingList(AppwriteModel): + """ + Embedding list + + Attributes + ---------- + total : float + Total number of embeddings that matched your query. + embeddings : List[Embedding] + List of embeddings. + """ + total: float = Field(..., alias='total') + embeddings: List[Embedding] = Field(..., alias='embeddings') diff --git a/appwrite/models/file.py b/appwrite/models/file.py index a49ee806..3657b451 100644 --- a/appwrite/models/file.py +++ b/appwrite/models/file.py @@ -21,6 +21,10 @@ class File(AppwriteModel): File permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). name : str File name. + folder : str + Virtual folder containing the file, with a trailing slash. Empty for the bucket root. + key : str + Full virtual path of the file: the folder followed by the file name. signature : str File MD5 signature. mimetype : str @@ -44,6 +48,8 @@ class File(AppwriteModel): updatedat: str = Field(..., alias='$updatedAt') permissions: List[Any] = Field(..., alias='$permissions') name: str = Field(..., alias='name') + folder: str = Field(..., alias='folder') + key: str = Field(..., alias='key') signature: str = Field(..., alias='signature') mimetype: str = Field(..., alias='mimeType') sizeoriginal: float = Field(..., alias='sizeOriginal') diff --git a/appwrite/models/mfa_challenge_secret.py b/appwrite/models/mfa_challenge_secret.py new file mode 100644 index 00000000..89beb284 --- /dev/null +++ b/appwrite/models/mfa_challenge_secret.py @@ -0,0 +1,27 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class MfaChallengeSecret(AppwriteModel): + """ + MFA Challenge Secret + + Attributes + ---------- + id : str + Token ID. + createdat : str + Token creation date in ISO 8601 format. + userid : str + User ID. + expire : str + Token expiration date in ISO 8601 format. + code : str + Challenge code to be delivered to the end user through a custom channel. + """ + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + userid: str = Field(..., alias='userId') + expire: str = Field(..., alias='expire') + code: str = Field(..., alias='code') diff --git a/appwrite/models/mfa_factors.py b/appwrite/models/mfa_factors.py index 1392c1d2..2d6953a1 100644 --- a/appwrite/models/mfa_factors.py +++ b/appwrite/models/mfa_factors.py @@ -17,8 +17,11 @@ class MfaFactors(AppwriteModel): Can email be used for MFA challenge for this account. recoverycode : bool Can recovery code be used for MFA challenge for this account. + custom : bool + Can custom factor be used for MFA challenge for this account. """ totp: bool = Field(..., alias='totp') phone: bool = Field(..., alias='phone') email: bool = Field(..., alias='email') recoverycode: bool = Field(..., alias='recoveryCode') + custom: bool = Field(..., alias='custom') diff --git a/appwrite/models/organization.py b/appwrite/models/organization.py index 95f4bdef..604be7d5 100644 --- a/appwrite/models/organization.py +++ b/appwrite/models/organization.py @@ -26,8 +26,8 @@ class Organization(AppwriteModel, Generic[T]): Total number of team members. prefs : Preferences[T] Team preferences as a key-value object - billingbudget : float - Project budget limit + billingbudget : Optional[float] + Project budget limit. Null when no budget is set. budgetalerts : List[Any] Project budget limit billingplan : str @@ -44,7 +44,7 @@ class Organization(AppwriteModel, Generic[T]): Current invoice cycle start date. billingnextinvoicedate : str Next invoice cycle start date. - billingtrialstartdate : str + billingtrialstartdate : Optional[str] Start date of trial. billingtrialdays : float Number of trial days. @@ -54,29 +54,29 @@ class Organization(AppwriteModel, Generic[T]): Current active aggregation id. paymentmethodid : str Default payment method. - billingaddressid : str + billingaddressid : Optional[str] Default payment method. - backuppaymentmethodid : str + backuppaymentmethodid : Optional[str] Backup payment method. status : str Team status. - remarks : str + remarks : Optional[str] Remarks on team status. - agreementbaa : str + agreementbaa : Optional[str] Organization agreements - programmanagername : str + programmanagername : Optional[str] Program manager's name. - programmanagercalendar : str + programmanagercalendar : Optional[str] Program manager's calendar link. - programdiscordchannelname : str + programdiscordchannelname : Optional[str] Program's discord channel name. - programdiscordchannelurl : str + programdiscordchannelurl : Optional[str] Program's discord channel URL. billinglimits : Optional[BillingLimits] Billing limits reached - billingplandowngrade : str + billingplandowngrade : Optional[str] Billing plan selected for downgrade. - billingtaxid : str + billingtaxid : Optional[str] Tax Id markedfordeletion : bool Marked for deletion @@ -91,7 +91,7 @@ class Organization(AppwriteModel, Generic[T]): name: str = Field(..., alias='name') total: float = Field(..., alias='total') prefs: Preferences[T] = Field(..., alias='prefs') - billingbudget: float = Field(..., alias='billingBudget') + billingbudget: Optional[float] = Field(default=None, alias='billingBudget') budgetalerts: List[Any] = Field(..., alias='budgetAlerts') billingplan: str = Field(..., alias='billingPlan') billingplanid: str = Field(..., alias='billingPlanId') @@ -100,23 +100,23 @@ class Organization(AppwriteModel, Generic[T]): billingstartdate: str = Field(..., alias='billingStartDate') billingcurrentinvoicedate: str = Field(..., alias='billingCurrentInvoiceDate') billingnextinvoicedate: str = Field(..., alias='billingNextInvoiceDate') - billingtrialstartdate: str = Field(..., alias='billingTrialStartDate') + billingtrialstartdate: Optional[str] = Field(default=None, alias='billingTrialStartDate') billingtrialdays: float = Field(..., alias='billingTrialDays') billingaggregationid: str = Field(..., alias='billingAggregationId') billinginvoiceid: str = Field(..., alias='billingInvoiceId') paymentmethodid: str = Field(..., alias='paymentMethodId') - billingaddressid: str = Field(..., alias='billingAddressId') - backuppaymentmethodid: str = Field(..., alias='backupPaymentMethodId') + billingaddressid: Optional[str] = Field(default=None, alias='billingAddressId') + backuppaymentmethodid: Optional[str] = Field(default=None, alias='backupPaymentMethodId') status: str = Field(..., alias='status') - remarks: str = Field(..., alias='remarks') - agreementbaa: str = Field(..., alias='agreementBAA') - programmanagername: str = Field(..., alias='programManagerName') - programmanagercalendar: str = Field(..., alias='programManagerCalendar') - programdiscordchannelname: str = Field(..., alias='programDiscordChannelName') - programdiscordchannelurl: str = Field(..., alias='programDiscordChannelUrl') + remarks: Optional[str] = Field(default=None, alias='remarks') + agreementbaa: Optional[str] = Field(default=None, alias='agreementBAA') + programmanagername: Optional[str] = Field(default=None, alias='programManagerName') + programmanagercalendar: Optional[str] = Field(default=None, alias='programManagerCalendar') + programdiscordchannelname: Optional[str] = Field(default=None, alias='programDiscordChannelName') + programdiscordchannelurl: Optional[str] = Field(default=None, alias='programDiscordChannelUrl') billinglimits: Optional[BillingLimits] = Field(default=None, alias='billingLimits') - billingplandowngrade: str = Field(..., alias='billingPlanDowngrade') - billingtaxid: str = Field(..., alias='billingTaxId') + billingplandowngrade: Optional[str] = Field(default=None, alias='billingPlanDowngrade') + billingtaxid: Optional[str] = Field(default=None, alias='billingTaxId') markedfordeletion: bool = Field(..., alias='markedForDeletion') platform: str = Field(..., alias='platform') projects: List[Any] = Field(..., alias='projects') diff --git a/appwrite/models/policy_list.py b/appwrite/models/policy_list.py index 3e579817..f00999b3 100644 --- a/appwrite/models/policy_list.py +++ b/appwrite/models/policy_list.py @@ -12,6 +12,7 @@ from .policy_session_limit import PolicySessionLimit from .policy_user_limit import PolicyUserLimit from .policy_membership_privacy import PolicyMembershipPrivacy +from .policy_mfa_factors import PolicyMfaFactors from .policy_deny_aliased_email import PolicyDenyAliasedEmail from .policy_deny_disposable_email import PolicyDenyDisposableEmail from .policy_deny_free_email import PolicyDenyFreeEmail @@ -25,8 +26,8 @@ class PolicyList(AppwriteModel): ---------- total : float Total number of policies in the given project. - policies : List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] + policies : List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] List of policies. """ total: float = Field(..., alias='total') - policies: List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] = Field(..., alias='policies') + policies: List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] = Field(..., alias='policies') diff --git a/appwrite/models/policy_mfa_factors.py b/appwrite/models/policy_mfa_factors.py new file mode 100644 index 00000000..8ff59740 --- /dev/null +++ b/appwrite/models/policy_mfa_factors.py @@ -0,0 +1,27 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class PolicyMfaFactors(AppwriteModel): + """ + Policy MFA Factors + + Attributes + ---------- + id : str + Policy ID. + totp : bool + Whether TOTP can be used to complete an MFA challenge. + email : bool + Whether email can be used to complete an MFA challenge. + phone : bool + Whether phone (SMS) can be used to complete an MFA challenge. + custom : bool + Whether the custom factor can be used to complete an MFA challenge. + """ + id: str = Field(..., alias='$id') + totp: bool = Field(..., alias='totp') + email: bool = Field(..., alias='email') + phone: bool = Field(..., alias='phone') + custom: bool = Field(..., alias='custom') diff --git a/appwrite/models/preferences.py b/appwrite/models/preferences.py index 73a68a21..5d655bd1 100644 --- a/appwrite/models/preferences.py +++ b/appwrite/models/preferences.py @@ -1,10 +1,12 @@ from typing import Any, Dict, List, Optional, Union, cast, Generic, TypeVar, Type -from pydantic import Field, PrivateAttr +from pydantic import Field, PrivateAttr, TypeAdapter, model_serializer from .base_model import AppwriteModel T = TypeVar('T') +_PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Preferences(AppwriteModel, Generic[T]): """ Preferences @@ -29,24 +31,37 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) - def model_dump(self, **kwargs) -> Dict[str, Any]: - result = super().model_dump(**kwargs) - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(**kwargs) - else: - result['data'] = self._data - return result - - def to_dict(self) -> Dict[str, Any]: - result = super().to_dict() - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(mode='json') - else: - result['data'] = self._data - return result + def _serialize_data(self, info, include=None, exclude=None): + if hasattr(self._data, 'model_dump'): + return self._data.model_dump( + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + if isinstance(self._data, dict) and (include is not None or exclude is not None): + return _PAYLOAD_ADAPTER.dump_python( + self._data, + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + return self._data + + @model_serializer(mode='wrap') + def _serialize_model(self, handler, info): + result = handler(self) + data = self._serialize_data(info, info.include, info.exclude) + if isinstance(result, dict) and isinstance(data, dict): + return {**result, **data} + + return data diff --git a/appwrite/models/project.py b/appwrite/models/project.py index 76822354..bc9abb12 100644 --- a/appwrite/models/project.py +++ b/appwrite/models/project.py @@ -81,6 +81,8 @@ class Project(AppwriteModel): OAuth2 server allowed scopes oauth2serverdefaultscopes : Optional[List[Any]] OAuth2 server scopes used when an authorization request omits the scope parameter + oauth2serverinstallationscopes : Optional[List[Any]] + Scopes an application may request when installed on a team oauth2serverauthorizationdetailstypes : Optional[List[Any]] OAuth2 server accepted RFC 9396 authorization_details types oauth2serveraccesstokenduration : Optional[float] @@ -139,6 +141,7 @@ class Project(AppwriteModel): oauth2serverauthorizationurl: Optional[str] = Field(default=None, alias='oAuth2ServerAuthorizationUrl') oauth2serverscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerScopes') oauth2serverdefaultscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerDefaultScopes') + oauth2serverinstallationscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerInstallationScopes') oauth2serverauthorizationdetailstypes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerAuthorizationDetailsTypes') oauth2serveraccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerAccessTokenDuration') oauth2serverrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerRefreshTokenDuration') diff --git a/appwrite/models/proxy_invalidation.py b/appwrite/models/proxy_invalidation.py new file mode 100644 index 00000000..511a0feb --- /dev/null +++ b/appwrite/models/proxy_invalidation.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class ProxyInvalidation(AppwriteModel): + """ + Invalidation + + Attributes + ---------- + domain : str + Domain name. + type : str + Invalidation type. Possible values are "tag", "path", or "all". + reference : str + Invalidated reference. Depending on type this is a cache tag name, a URL path, or empty when type is all. + status : str + Invalidation status. + """ + domain: str = Field(..., alias='domain') + type: str = Field(..., alias='type') + reference: str = Field(..., alias='reference') + status: str = Field(..., alias='status') diff --git a/appwrite/models/row.py b/appwrite/models/row.py index e6e15976..f421cd17 100644 --- a/appwrite/models/row.py +++ b/appwrite/models/row.py @@ -1,10 +1,12 @@ from typing import Any, Dict, List, Optional, Union, cast, Generic, TypeVar, Type -from pydantic import Field, PrivateAttr +from pydantic import Field, PrivateAttr, TypeAdapter, model_serializer from .base_model import AppwriteModel T = TypeVar('T') +_PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Row(AppwriteModel, Generic[T]): """ Row @@ -57,24 +59,63 @@ def data(self) -> T: def data(self, value: T) -> None: object.__setattr__(self, '_data', value) - def model_dump(self, **kwargs) -> Dict[str, Any]: - result = super().model_dump(**kwargs) - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(**kwargs) - else: - result['data'] = self._data - return result + def _serialize_data(self, info, include=None, exclude=None): + if hasattr(self._data, 'model_dump'): + return self._data.model_dump( + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + if isinstance(self._data, dict) and (include is not None or exclude is not None): + return _PAYLOAD_ADAPTER.dump_python( + self._data, + mode=info.mode, + by_alias=info.by_alias, + exclude_unset=info.exclude_unset, + exclude_defaults=info.exclude_defaults, + exclude_none=info.exclude_none, + include=include, + exclude=exclude, + ) + + return self._data + + @staticmethod + def _select_data(selector): + """ + Resolves a pydantic include/exclude selector against the 'data' key, which is + serialized here rather than declared as a field. Returns whether the key was + named, and any nested selector to apply within it. + """ + if selector is None: + return False, None + + if isinstance(selector, dict): + if 'data' not in selector: + return False, None + + nested = selector['data'] + + return True, nested if isinstance(nested, (dict, set, frozenset, list, tuple)) else None + + return 'data' in selector, None + + @model_serializer(mode='wrap') + def _serialize_model(self, handler, info): + result = handler(self) + included, include_fields = self._select_data(info.include) + excluded, exclude_fields = self._select_data(info.exclude) + + if info.include is not None and not included: + return result + + if excluded and exclude_fields is None: + return result - def to_dict(self) -> Dict[str, Any]: - result = super().to_dict() - if hasattr(self, '_data'): - if isinstance(self._data, dict): - result['data'] = self._data - elif hasattr(self._data, 'model_dump'): - result['data'] = self._data.model_dump(mode='json') - else: - result['data'] = self._data + result['data'] = self._serialize_data(info, include_fields, exclude_fields) return result diff --git a/appwrite/models/row_list.py b/appwrite/models/row_list.py index 86ca37ad..b4508b2a 100644 --- a/appwrite/models/row_list.py +++ b/appwrite/models/row_list.py @@ -26,7 +26,7 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'RowList instance = cls.model_validate(data) if 'rows' in data and data['rows'] is not None: instance.rows = [ - Row.with_data(row, model_type) + Row.with_data(row, model_type) for row in data['rows'] ] return instance diff --git a/appwrite/models/team_list.py b/appwrite/models/team_list.py index 81602c9b..85610b5c 100644 --- a/appwrite/models/team_list.py +++ b/appwrite/models/team_list.py @@ -26,7 +26,7 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'TeamLis instance = cls.model_validate(data) if 'teams' in data and data['teams'] is not None: instance.teams = [ - Team.with_data(row, model_type) + Team.with_data(row, model_type) for row in data['teams'] ] return instance diff --git a/appwrite/models/usage_billing_plan.py b/appwrite/models/usage_billing_plan.py index a078e726..40016c29 100644 --- a/appwrite/models/usage_billing_plan.py +++ b/appwrite/models/usage_billing_plan.py @@ -14,13 +14,13 @@ class UsageBillingPlan(AppwriteModel): Bandwidth additional resources executions : AdditionalResource Executions additional resources - member : AdditionalResource + member : Optional[AdditionalResource] Member additional resources realtime : AdditionalResource Realtime additional resources realtimemessages : AdditionalResource Realtime messages additional resources - realtimebandwidth : AdditionalResource + realtimebandwidth : Optional[AdditionalResource] Realtime bandwidth additional resources storage : AdditionalResource Storage additional resources @@ -30,17 +30,17 @@ class UsageBillingPlan(AppwriteModel): GBHour additional resources imagetransformations : AdditionalResource Image transformation additional resources - credits : AdditionalResource + credits : Optional[AdditionalResource] Credits additional resources """ bandwidth: AdditionalResource = Field(..., alias='bandwidth') executions: AdditionalResource = Field(..., alias='executions') - member: AdditionalResource = Field(..., alias='member') + member: Optional[AdditionalResource] = Field(default=None, alias='member') realtime: AdditionalResource = Field(..., alias='realtime') realtimemessages: AdditionalResource = Field(..., alias='realtimeMessages') - realtimebandwidth: AdditionalResource = Field(..., alias='realtimeBandwidth') + realtimebandwidth: Optional[AdditionalResource] = Field(default=None, alias='realtimeBandwidth') storage: AdditionalResource = Field(..., alias='storage') users: AdditionalResource = Field(..., alias='users') gbhours: AdditionalResource = Field(..., alias='GBHours') imagetransformations: AdditionalResource = Field(..., alias='imageTransformations') - credits: AdditionalResource = Field(..., alias='credits') + credits: Optional[AdditionalResource] = Field(default=None, alias='credits') diff --git a/appwrite/models/user_list.py b/appwrite/models/user_list.py index c6c2e627..fa071b9c 100644 --- a/appwrite/models/user_list.py +++ b/appwrite/models/user_list.py @@ -26,7 +26,7 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'UserLis instance = cls.model_validate(data) if 'users' in data and data['users'] is not None: instance.users = [ - User.with_data(row, model_type) + User.with_data(row, model_type) for row in data['users'] ] return instance diff --git a/appwrite/service.py b/appwrite/service.py index dcf43a08..fef16a05 100644 --- a/appwrite/service.py +++ b/appwrite/service.py @@ -46,5 +46,6 @@ def _parse_response( return model.model_validate(response) except ValidationError as error: raise AppwriteException( - f'Unable to parse response into {model.__name__}: {error}' + f'Unable to parse response into {model.__name__}: {error}', + response=response, ) from error diff --git a/appwrite/services/account.py b/appwrite/services/account.py index 492d9102..ee1f0f96 100644 --- a/appwrite/services/account.py +++ b/appwrite/services/account.py @@ -9,7 +9,6 @@ from ..models.oauth2_consent_token_list import Oauth2ConsentTokenList from ..models.oauth2_consent_token import Oauth2ConsentToken from ..models.identity_list import IdentityList -from ..models.jwt import Jwt from ..models.log_list import LogList from ..enums.authenticator_type import AuthenticatorType from ..models.mfa_type import MfaType @@ -525,44 +524,6 @@ def delete_identity( return response - def create_jwt( - self, - duration: Optional[float] = None - ) -> Jwt: - """ - Use this endpoint to create a JSON Web Token. You can use the resulting JWT to authenticate on behalf of the current user when working with the Appwrite server-side API and SDKs. The JWT secret is valid for 15 minutes from its creation and will be invalid if the user will logout in that time frame. - - Parameters - ---------- - duration : Optional[float] - Time in seconds before JWT expires. Default duration is 900 seconds, and maximum is 3600 seconds. - - Returns - ------- - Jwt - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/account/jwts' - api_params = {} - - if duration is not None: - api_params['duration'] = self._normalize_value(duration) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=Jwt) - - def list_logs( self, queries: Optional[List[str]] = None, @@ -789,7 +750,7 @@ def create_mfa_challenge( Parameters ---------- factor : AuthenticationFactor - Factor used for verification. Must be one of following: `email`, `phone`, `totp`, `recoveryCode`. + Factor used for verification. Must be one of following: `email`, `phone`, `totp`, `recoveryCode`, `custom`. Returns ------- diff --git a/appwrite/services/activities.py b/appwrite/services/activities.py index 0d1e5b5b..a534716d 100644 --- a/appwrite/services/activities.py +++ b/appwrite/services/activities.py @@ -13,14 +13,14 @@ def __init__(self, client) -> None: def list_events( self, - queries: Optional[str] = None + queries: Optional[List[str]] = None ) -> ActivityEventList: """ List all events for selected filters. Parameters ---------- - queries : Optional[str] + queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/databases#querying-documents). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on attributes such as userId, teamId, etc. Returns diff --git a/appwrite/services/apps.py b/appwrite/services/apps.py index d4a3f681..bd0e6f90 100644 --- a/appwrite/services/apps.py +++ b/appwrite/services/apps.py @@ -262,7 +262,7 @@ def get( Parameters ---------- app_id : str - Application unique ID or HTTPS client ID metadata document URL. + Application unique ID. Returns ------- @@ -356,7 +356,7 @@ def update( device_flow : Optional[bool] Allow this client to use the OAuth2 Device Authorization Grant (RFC 8628) for input-constrained devices such as TVs and CLIs. Defaults to false. installation_scopes : Optional[List[str]] - Scopes the application requests when installed on a team. Organization-level and project-level scopes only; use the list scopes endpoint with `type=installation` to discover available values. Maximum of 100 scopes are allowed. + Scopes the application requests when installed on a team. Only scopes allowed by the project's OAuth2 server installation scopes configuration are accepted; use the list installation scopes endpoint to discover available values. Maximum of 100 scopes are allowed. installation_redirect_url : Optional[str] URL users are redirected to after creating or updating an installation of this application. Must be an https URL, an http loopback URL (localhost, 127.0.0.1, [::1]), or a private-use scheme URI, and must not contain a fragment. Leave empty for no redirect. @@ -475,7 +475,7 @@ def list_installations( total: Optional[bool] = None ) -> AppInstallationList: """ - List installations of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. + List installations of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. Parameters ---------- @@ -523,7 +523,7 @@ def get_installation( installation_id: str ) -> AppInstallation: """ - Get an installation of an application by its unique ID. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. + Get an installation of an application by its unique ID. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. Parameters ---------- @@ -563,13 +563,60 @@ def get_installation( return self._parse_response(response, model=AppInstallation) + def delete_installation( + self, + app_id: str, + installation_id: str + ) -> Dict[str, Any]: + """ + Delete an installation of an application by its unique ID. Requires a caller with update access to the app. Previously issued installation access tokens are revoked. + + Parameters + ---------- + app_id : str + Application unique ID. + installation_id : str + Installation unique ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/apps/{appId}/installations/{installationId}' + api_params = {} + if app_id is None: + raise AppwriteException('Missing required parameter: "app_id"') + + if installation_id is None: + raise AppwriteException('Missing required parameter: "installation_id"') + + api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) + api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + def create_installation_token( self, app_id: str, installation_id: str ) -> Oauth2Token: """ - Create a token for an installation of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header. The returned token carries the scopes and authorization details granted to the installation, and can be used as an `Authorization: Bearer` header everywhere OAuth2 access tokens are accepted. Multiple tokens can be active for the same installation at once; each token stays valid until it expires or the installation is updated or deleted. + Create a token for an installation of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. The returned token carries the scopes and authorization details granted to the installation, and can be used as an `Authorization: Bearer` header everywhere OAuth2 access tokens are accepted. Multiple tokens can be active for the same installation at once; each token stays valid until it expires or the installation is updated or deleted. Parameters ---------- diff --git a/appwrite/services/backups.py b/appwrite/services/backups.py index c8b782c5..cc41ff09 100644 --- a/appwrite/services/backups.py +++ b/appwrite/services/backups.py @@ -439,13 +439,13 @@ def create_restoration( """ Create and trigger a new restoration for a backup on a project. - For a backup of one database, the restoration resolves its destination before it is queued. Pass `newResourceId` to restore into that database ID, including the archived database ID to overwrite it. When `newResourceId` is omitted, a new database ID is generated and returned in `options`. + For a backup of one database, the restoration resolves its destination before it is queued. When `newResourceId` is omitted, the archived database is restored in place and its own ID is returned in `options`. Pass a different `newResourceId` to restore alongside it as a new database instead. The restoration migration records the archived database in `resourceId` and `resourceType`, and the resolved database in `destinationResourceId` and `destinationResourceType`. Database types are stored canonically as `database`, `documentsdb`, or `vectorsdb`. Project-wide restorations leave these fields empty because they do not have a single source or destination database. To list every migration related to one database, use its canonical type in a nested `OR(AND(...), AND(...), AND(...))` across the root, parent, and destination relation pairs: `(resourceType, resourceId)`, `(parentResourceType, parentResourceId)`, and `(destinationResourceType, destinationResourceId)`. Legacy and TablesDB databases use `database`; the operational `resourceType` of a table migration is not rewritten to `tablesdb`. - When restoring a DocumentsDB or VectorsDB database to a new resource from a dedicated source, the restore provisions a fresh dedicated backing database at the source database's own specification. + When restoring a DocumentsDB or VectorsDB database from a dedicated source, the restore provisions a fresh dedicated backing database at the source database's own specification and lands the data there. An in-place restore swaps the database onto that backing only once the restore has succeeded, and retires the backing it displaced only once that swap is confirmed, so the source keeps serving its own data until the restored data is in place and any failure leaves it untouched. A serverless source has no dedicated backing to clone and restores onto the archived database instead. Parameters @@ -455,7 +455,7 @@ def create_restoration( services : List[BackupServices] Array of services to restore new_resource_id : Optional[str] - Destination resource ID. Omit to generate a new ID, or pass the archived resource ID to overwrite it. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + Destination resource ID. Omit to restore the archived resource in place, or pass a different ID to restore alongside it as a new resource. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. new_resource_name : Optional[str] Database name. Max length: 128 chars. diff --git a/appwrite/services/databases.py b/appwrite/services/databases.py index 51831aec..32c63923 100644 --- a/appwrite/services/databases.py +++ b/appwrite/services/databases.py @@ -642,7 +642,7 @@ def create_collection( enabled : Optional[bool] Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. attributes : Optional[List[Dict[str, Any]]] - Array of attribute definitions to create. Each attribute should contain: key (string), type (string: string, integer, float, boolean, datetime), size (integer, required for string type), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. + Array of attribute definitions to create. Each attribute should contain: key (string), type (string: string, varchar, text, mediumtext, longtext, integer, bigint, double, boolean, datetime, point, linestring, polygon, email, url, ip, enum), size (integer, required for string and varchar types), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. indexes : Optional[List[Dict[str, Any]]] Array of index definitions to create. Each index should contain: key (string), type (string: key, fulltext, unique, spatial), attributes (array of attribute keys), orders (array of ASC/DESC, optional), and lengths (array of integers, optional). @@ -2951,7 +2951,7 @@ def create_relationship_attribute( related_collection_id : str Related Collection ID. type : RelationshipType - Relation type + Relationship type. Possible values are: oneToOne, oneToMany, manyToOne, manyToMany. two_way : Optional[bool] Is Two Way? key : Optional[str] @@ -2959,7 +2959,7 @@ def create_relationship_attribute( two_way_key : Optional[str] Two Way Attribute Key. on_delete : Optional[RelationMutate] - Constraints option + Delete constraint. Possible values are: cascade, restrict, setNull. Returns ------- @@ -3033,7 +3033,7 @@ def update_relationship_attribute( key : str Attribute Key. on_delete : Optional[RelationMutate] - Constraints option + Delete constraint. Possible values are: cascade, restrict, setNull. new_key : Optional[str] New Attribute Key. diff --git a/appwrite/services/embeddings.py b/appwrite/services/embeddings.py new file mode 100644 index 00000000..50848d06 --- /dev/null +++ b/appwrite/services/embeddings.py @@ -0,0 +1,58 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..enums.embedding_model import EmbeddingModel +from ..models.embedding_list import EmbeddingList + +class Embeddings(Service): + + def __init__(self, client) -> None: + super(Embeddings, self).__init__(client) + + def create_text_embeddings( + self, + texts: List[str], + model: Optional[EmbeddingModel] = None + ) -> EmbeddingList: + """ + Generate vector embeddings for an array of text using the selected embedding model. Use the returned vectors to power semantic search and similarity queries against your vector collections. + + + Parameters + ---------- + texts : List[str] + Array of text to generate embeddings. + model : Optional[EmbeddingModel] + The embedding model to use for generating vector embeddings. + + Returns + ------- + EmbeddingList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/embeddings/text' + api_params = {} + if texts is None: + raise AppwriteException('Missing required parameter: "texts"') + + + api_params['texts'] = self._normalize_value(texts) + if model is not None: + api_params['model'] = self._normalize_value(model) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=EmbeddingList) + diff --git a/appwrite/services/functions.py b/appwrite/services/functions.py index 4b0f552f..07bd41b4 100644 --- a/appwrite/services/functions.py +++ b/appwrite/services/functions.py @@ -260,7 +260,7 @@ def list_specifications( Parameters ---------- type : Optional[str] - Specification type to list. Can be one of: runtimes, builds. + Specification type to list. Can be one of: runtimes, builds. Defaults to runtimes. Returns ------- diff --git a/appwrite/services/project.py b/appwrite/services/project.py index 38af962f..1665fa81 100644 --- a/appwrite/services/project.py +++ b/appwrite/services/project.py @@ -7,8 +7,8 @@ from ..enums.project_auth_method_id import ProjectAuthMethodId from ..models.key_list import KeyList from ..enums.project_key_scopes import ProjectKeyScopes -from ..models.key import Key from ..models.ephemeral_key import EphemeralKey +from ..models.key import Key from ..models.mock_number_list import MockNumberList from ..models.mock_number import MockNumber from ..models.o_auth2_provider_list import OAuth2ProviderList @@ -74,6 +74,7 @@ from ..models.policy_session_limit import PolicySessionLimit from ..models.policy_user_limit import PolicyUserLimit from ..models.policy_membership_privacy import PolicyMembershipPrivacy +from ..models.policy_mfa_factors import PolicyMfaFactors from ..models.policy_deny_aliased_email import PolicyDenyAliasedEmail from ..models.policy_deny_disposable_email import PolicyDenyDisposableEmail from ..models.policy_deny_free_email import PolicyDenyFreeEmail @@ -237,67 +238,6 @@ def list_keys( return self._parse_response(response, model=KeyList) - def create_key( - self, - key_id: str, - name: str, - scopes: List[ProjectKeyScopes], - expire: Optional[str] = None - ) -> Key: - """ - Create a new API key. It's recommended to have multiple API keys with strict scopes for separate functions within your project. - - You can also create an ephemeral API key if you need a short-lived key instead. - - Parameters - ---------- - key_id : str - Key ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - name : str - Key name. Max length: 128 chars. - scopes : List[ProjectKeyScopes] - Key scopes list. Maximum of 200 scopes are allowed. - expire : Optional[str] - Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. - - Returns - ------- - Key - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/project/keys' - api_params = {} - if key_id is None: - raise AppwriteException('Missing required parameter: "key_id"') - - if name is None: - raise AppwriteException('Missing required parameter: "name"') - - if scopes is None: - raise AppwriteException('Missing required parameter: "scopes"') - - - api_params['keyId'] = self._normalize_value(key_id) - api_params['name'] = self._normalize_value(name) - api_params['scopes'] = self._normalize_value(scopes) - if expire is not None: - api_params['expire'] = self._normalize_value(expire) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=Key) - - def create_ephemeral_key( self, scopes: List[ProjectKeyScopes], @@ -796,7 +736,8 @@ def update_o_auth2_server( user_code_length: Optional[float] = None, user_code_format: Optional[str] = None, device_code_duration: Optional[float] = None, - default_scopes: Optional[List[str]] = None + default_scopes: Optional[List[str]] = None, + installation_scopes: Optional[List[str]] = None ) -> ProjectModel: """ Update the OAuth2 server (OIDC provider) configuration. @@ -833,6 +774,8 @@ def update_o_auth2_server( Lifetime in seconds of device flow device codes and user codes. Device codes are intentionally short-lived. Leave empty to use default 600. default_scopes : Optional[List[str]] List of OAuth2 scopes used when an authorization request omits the scope parameter. Every default scope must also be allowed by the OAuth2 server. Maximum of 100 scopes are allowed, each up to 128 characters long. + installation_scopes : Optional[List[str]] + List of scopes an application may request when installed on a team. Omitting the parameter clears the list, so no installation scopes can be granted. Maximum of 100 scopes are allowed, each up to 128 characters long. Returns ------- @@ -882,6 +825,8 @@ def update_o_auth2_server( api_params['deviceCodeDuration'] = self._normalize_value(device_code_duration) if default_scopes is not None: api_params['defaultScopes'] = self._normalize_value(default_scopes) + if installation_scopes is not None: + api_params['installationScopes'] = self._normalize_value(installation_scopes) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -4149,6 +4094,59 @@ def update_membership_privacy_policy( return self._parse_response(response, model=ProjectModel) + def update_mfa_factors_policy( + self, + totp: Optional[bool] = None, + email: Optional[bool] = None, + phone: Optional[bool] = None, + custom: Optional[bool] = None + ) -> ProjectModel: + """ + Updating this policy allows you to control which factors users can use to complete an MFA challenge. Disabled factors cannot be used to create a challenge and are reported as unavailable when listing factors. The custom factor is disabled by default; enable it to deliver challenge codes through your own channel. Recovery codes always remain available as a fallback. + + Parameters + ---------- + totp : Optional[bool] + Set to true to allow TOTP to complete an MFA challenge, or false to disable it. + email : Optional[bool] + Set to true to allow email to complete an MFA challenge, or false to disable it. + phone : Optional[bool] + Set to true to allow phone (SMS) to complete an MFA challenge, or false to disable it. + custom : Optional[bool] + Set to true to allow the custom factor to complete an MFA challenge, or false to disable it. + + Returns + ------- + ProjectModel + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/project/policies/mfa-factors' + api_params = {} + + if totp is not None: + api_params['totp'] = self._normalize_value(totp) + if email is not None: + api_params['email'] = self._normalize_value(email) + if phone is not None: + api_params['phone'] = self._normalize_value(phone) + if custom is not None: + api_params['custom'] = self._normalize_value(custom) + + response = self.client.call('patch', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=ProjectModel) + + def update_password_dictionary_policy( self, enabled: bool @@ -4201,7 +4199,7 @@ def update_password_history_policy( Parameters ---------- total : Optional[float] - Set the password history length per user. Value can be between 1 and 5000, or null to disable the limit. + Set the password history length per user. Value can be between 1 and 20, or null to disable the limit. Returns ------- @@ -4376,7 +4374,7 @@ def update_session_duration_policy( Parameters ---------- duration : float - Maximum session length in seconds. Minium allowed value is 5 second, and maximum is 1 year, which is 31536000 seconds. + Maximum session length in seconds. Minium allowed value is 60 seconds, and maximum is 1 year, which is 31536000 seconds. Returns ------- @@ -4448,15 +4446,15 @@ def update_session_invalidation_policy( def update_session_limit_policy( self, - total: Optional[float] + total: float ) -> ProjectModel: """ Update the maximum number of sessions allowed per user. When the limit is hit, the oldest session will be deleted to make room for new one. Parameters ---------- - total : Optional[float] - Set the maximum number of sessions allowed per user. Value can be between 1 and 5000, or null to disable the limit. + total : float + Set the maximum number of sessions allowed per user. Value can be between 1 and 100. Returns ------- @@ -4471,6 +4469,9 @@ def update_session_limit_policy( api_path = '/project/policies/session-limit' api_params = {} + if total is None: + raise AppwriteException('Missing required parameter: "total"') + api_params['total'] = self._normalize_value(total) @@ -4493,7 +4494,7 @@ def update_user_limit_policy( Parameters ---------- total : Optional[float] - Set the maximum number of users allowed in the project. Value can be between 1 and 5000, or null to disable the limit. + Set the maximum number of users allowed in the project. Value can be between 0 and 10000. Use 0 or null to disable the limit. Returns ------- @@ -4523,18 +4524,18 @@ def update_user_limit_policy( def get_policy( self, policy_id: ProjectPolicyId - ) -> Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]: + ) -> Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]: """ Get a policy by its unique ID. This endpoint returns the current configuration for the requested project policy. Parameters ---------- policy_id : ProjectPolicyId - Policy ID. Can be one of: password-dictionary, password-history, password-strength, password-personal-data, session-alert, session-duration, session-invalidation, session-limit, user-limit, membership-privacy, deny-aliased-email, deny-disposable-email, deny-free-email, deny-corporate-email. + Policy ID. Can be one of: password-dictionary, password-history, password-strength, password-personal-data, session-alert, session-duration, session-invalidation, session-limit, user-limit, membership-privacy, mfa-factors, deny-aliased-email, deny-disposable-email, deny-free-email, deny-corporate-email. Returns ------- - Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail] + Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail] API response as one of the typed response models Raises @@ -4588,6 +4589,9 @@ def get_policy( if response.get('$id') == 'membership-privacy': return self._parse_response(response, model=PolicyMembershipPrivacy) + if response.get('$id') == 'mfa-factors': + return self._parse_response(response, model=PolicyMfaFactors) + if response.get('$id') == 'deny-aliased-email': return self._parse_response(response, model=PolicyDenyAliasedEmail) diff --git a/appwrite/services/proxy.py b/appwrite/services/proxy.py index 44f18747..ce209139 100644 --- a/appwrite/services/proxy.py +++ b/appwrite/services/proxy.py @@ -3,6 +3,8 @@ from typing import Any, Dict, List, Optional, Union from ..exception import AppwriteException from appwrite.utils.deprecated import deprecated +from ..enums.invalidation_type import InvalidationType +from ..models.proxy_invalidation import ProxyInvalidation from ..models.proxy_rule_list import ProxyRuleList from ..models.proxy_rule import ProxyRule from ..enums.status_code import StatusCode @@ -13,6 +15,60 @@ class Proxy(Service): def __init__(self, client) -> None: super(Proxy, self).__init__(client) + def create_invalidation( + self, + domain: str, + type: InvalidationType, + reference: Optional[str] = None + ) -> ProxyInvalidation: + """ + Create a new CDN cache invalidation for a domain. Executes a hard purge of cached content. + + Depending on type, the invalidation purges a single cache tag, a single URL path, or all cached content for the domain. + + Parameters + ---------- + domain : str + Domain name. + type : InvalidationType + Type of reference passed. Allowed values are: tag, path, all + reference : Optional[str] + Reference to invalidate. Depending on type this can be: cache tag name (up to 128 characters), URL path (up to 2048 characters). Not required when type is all. + + Returns + ------- + ProxyInvalidation + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/proxy/invalidations' + api_params = {} + if domain is None: + raise AppwriteException('Missing required parameter: "domain"') + + if type is None: + raise AppwriteException('Missing required parameter: "type"') + + + api_params['domain'] = self._normalize_value(domain) + api_params['type'] = self._normalize_value(type) + if reference is not None: + api_params['reference'] = self._normalize_value(reference) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=ProxyInvalidation) + + def list_rules( self, queries: Optional[List[str]] = None, diff --git a/appwrite/services/sites.py b/appwrite/services/sites.py index bcf0c1ad..8b930f17 100644 --- a/appwrite/services/sites.py +++ b/appwrite/services/sites.py @@ -267,7 +267,7 @@ def list_specifications( Parameters ---------- type : Optional[str] - Specification type to list. Can be one of: runtimes, builds. + Specification type to list. Can be one of: runtimes, builds. Defaults to runtimes. Returns ------- diff --git a/appwrite/services/storage.py b/appwrite/services/storage.py index a450e58b..7511db08 100644 --- a/appwrite/services/storage.py +++ b/appwrite/services/storage.py @@ -341,7 +341,7 @@ def list_files( bucket_id : str Storage bucket unique ID. You can create a new storage bucket using the Storage service [server integration](https://appwrite.io/docs/server/storage#createBucket). queries : Optional[List[str]] - Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, signature, mimeType, sizeOriginal, chunksTotal, chunksUploaded + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, folder, signature, mimeType, sizeOriginal, chunksTotal, chunksUploaded search : Optional[str] Search term to filter your list results. Max length: 256 chars. total : Optional[bool] @@ -386,6 +386,7 @@ def create_file( file_id: str, file: InputFile, permissions: Optional[List[str]] = None, + folder: Optional[str] = None, on_progress = None ) -> File: """ @@ -408,6 +409,8 @@ def create_file( Binary file. Appwrite SDKs provide helpers to handle file input. [Learn about file input](https://appwrite.io/docs/products/storage/upload-download#input-file). permissions : Optional[List[str]] An array of permission strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + folder : Optional[str] + Virtual folder to place the file in, for example "photos/2026". Nest folders with `/`. Defaults to the bucket root. on_progress : callable, optional Optional callback for upload progress @@ -439,6 +442,8 @@ def create_file( api_params['file'] = self._normalize_value(file) if permissions is not None: api_params['permissions'] = self._normalize_value(permissions) + if folder is not None: + api_params['folder'] = self._normalize_value(folder) param_name = 'file' diff --git a/appwrite/services/tables_db.py b/appwrite/services/tables_db.py index f84f9cca..94854111 100644 --- a/appwrite/services/tables_db.py +++ b/appwrite/services/tables_db.py @@ -9,6 +9,9 @@ from ..models.transaction_list import TransactionList from ..models.transaction import Transaction from ..models.dedicated_database import DedicatedDatabase +from ..models.database_migration_list import DatabaseMigrationList +from ..models.database_migration import DatabaseMigration +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas from ..models.database_status import DatabaseStatus from ..models.table_list import TableList @@ -101,7 +104,8 @@ def create( name: str, enabled: Optional[bool] = None, specification: Optional[str] = None, - replicas: Optional[float] = None + replicas: Optional[float] = None, + sync_mode: Optional[str] = None ) -> Database: """ Create a new Database. @@ -119,6 +123,8 @@ def create( Database specification. Defaults to `serverless`, which creates the database on the shared pool. Any other value provisions a dedicated database on that specification. replicas : Optional[float] Number of high availability replicas (0-5) for the dedicated database backing this database. Requires a dedicated `specification`; must be 0 for a serverless database. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Requires a dedicated `specification`; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. Returns ------- @@ -148,6 +154,8 @@ def create( api_params['specification'] = self._normalize_value(specification) if replicas is not None: api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) response = self.client.call('post', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -478,7 +486,9 @@ def update( database_id: str, name: Optional[str] = None, enabled: Optional[bool] = None, - replicas: Optional[float] = None + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None ) -> Database: """ Update a database by its unique ID. @@ -491,8 +501,12 @@ def update( Database name. Max length: 128 chars. enabled : Optional[bool] Is database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + specification : Optional[str] + Database specification. Resizing between dedicated specifications changes cpu, memory, storage and the connection ceiling via a rolling cutover with zero downtime. Moving a `serverless` database onto a dedicated specification is a data migration, not a resize. replicas : Optional[float] Number of high availability replicas (0-5) for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. Returns ------- @@ -516,8 +530,12 @@ def update( api_params['name'] = self._normalize_value(name) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) if replicas is not None: api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) response = self.client.call('put', api_path, { 'X-Appwrite-Project': self.client.get_config('project'), @@ -573,7 +591,7 @@ def create_failover( target_replica_id: Optional[str] = None ) -> DedicatedDatabase: """ - Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation by a failover that did not finish also accepts this call as a repair, provided `targetReplicaId` names the member to promote. Parameters ---------- @@ -612,6 +630,291 @@ def create_failover( return self._parse_response(response, model=DedicatedDatabase) + def list_migrations( + self, + database_id: str + ) -> DatabaseMigrationList: + """ + List the dedicated migrations for a TablesDB database. A database has at most one in-flight migration. + + Parameters + ---------- + database_id : str + Database ID. + + Returns + ------- + DatabaseMigrationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/migrations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DatabaseMigrationList) + + + def create_migration( + self, + database_id: str, + specification: str, + auto_cutover: Optional[bool] = None + ) -> DatabaseMigration: + """ + Start migrating a serverless TablesDB database onto a dedicated MySQL compute. Data is copied to the target while the source stays live, with a brief read-only window during cutover. + + Parameters + ---------- + database_id : str + Database ID. + specification : str + Dedicated compute specification to provision as the migration target (e.g. s-2vcpu-4gb). The migration always targets a dedicated compute, so `serverless` is not accepted. + auto_cutover : Optional[bool] + Whether to cut over automatically once the copy is verified. When disabled the migration parks at ready_to_cutover and holds there until the cutover is performed manually. + + Returns + ------- + DatabaseMigration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/migrations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + if specification is None: + raise AppwriteException('Missing required parameter: "specification"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + api_params['specification'] = self._normalize_value(specification) + if auto_cutover is not None: + api_params['autoCutover'] = self._normalize_value(auto_cutover) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DatabaseMigration) + + + def get_migration( + self, + database_id: str, + migration_id: str + ) -> DatabaseMigration: + """ + Get a single dedicated migration for a TablesDB database by its ID. + + Parameters + ---------- + database_id : str + Database ID. + migration_id : str + Migration ID. + + Returns + ------- + DatabaseMigration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/migrations/{migrationId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + if migration_id is None: + raise AppwriteException('Missing required parameter: "migration_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DatabaseMigration) + + + def delete_migration( + self, + database_id: str, + migration_id: str + ) -> Dict[str, Any]: + """ + Abort an in-flight TablesDB dedicated migration. Only allowed before cutover; once the migration has cut over it cannot be aborted. + + Parameters + ---------- + database_id : str + Database ID. + migration_id : str + Migration ID. + + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/migrations/{migrationId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + if migration_id is None: + raise AppwriteException('Missing required parameter: "migration_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) + + + response = self.client.call('delete', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return response + + + def cutover_migration( + self, + database_id: str, + migration_id: str + ) -> DatabaseMigration: + """ + Cut a verified TablesDB migration over to its dedicated compute. Only applies to a migration created with `autoCutover` disabled, which waits at `ready_to_cutover` until this is called. The routing flip happens shortly after this returns, with a brief read-only window. One call buys one attempt: a cutover that fails a check returns the migration to `verifying` and parks it again, so call this once more to retry. + + Parameters + ---------- + database_id : str + Database ID. + migration_id : str + Migration ID. + + Returns + ------- + DatabaseMigration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/migrations/{migrationId}/cutover' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + if migration_id is None: + raise AppwriteException('Missing required parameter: "migration_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) + + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DatabaseMigration) + + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/tablesdb/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_replicas( self, database_id: str @@ -773,7 +1076,7 @@ def create_table( enabled : Optional[bool] Is table enabled? When set to 'disabled', users cannot access the table but Server SDKs with and API key can still read and write to the table. No data is lost when this is toggled. columns : Optional[List[Dict[str, Any]]] - Array of column definitions to create. Each column should contain: key (string), type (string: string, integer, float, boolean, datetime, relationship), size (integer, required for string type), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. + Array of column definitions to create. Each column should contain: key (string), type (string: string, varchar, text, mediumtext, longtext, integer, bigint, double, boolean, datetime, point, linestring, polygon, email, url, ip, enum), size (integer, required for string and varchar types), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. indexes : Optional[List[Dict[str, Any]]] Array of index definitions to create. Each index should contain: key (string), type (string: key, fulltext, unique, spatial), attributes (array of column keys), orders (array of ASC/DESC, optional), and lengths (array of integers, optional). @@ -2988,7 +3291,7 @@ def create_relationship_column( related_table_id : str Related Table ID. type : RelationshipType - Relation type + Relationship type. Possible values are: oneToOne, oneToMany, manyToOne, manyToMany. two_way : Optional[bool] Is Two Way? key : Optional[str] @@ -2996,7 +3299,7 @@ def create_relationship_column( two_way_key : Optional[str] Two Way Column Key. on_delete : Optional[RelationMutate] - Constraints option + Delete constraint. Possible values are: cascade, restrict, setNull. Returns ------- @@ -3822,7 +4125,7 @@ def update_relationship_column( key : str Column Key. on_delete : Optional[RelationMutate] - Constraints option + Delete constraint. Possible values are: cascade, restrict, setNull. new_key : Optional[str] New Column Key. diff --git a/appwrite/services/users.py b/appwrite/services/users.py index 8eab2dc7..fad7bd3c 100644 --- a/appwrite/services/users.py +++ b/appwrite/services/users.py @@ -11,6 +11,7 @@ from ..models.log_list import LogList from ..models.membership_list import MembershipList from ..enums.authenticator_type import AuthenticatorType +from ..models.mfa_challenge_secret import MfaChallengeSecret from ..models.mfa_factors import MfaFactors from ..models.mfa_recovery_codes import MfaRecoveryCodes from ..models.preferences import Preferences @@ -1219,6 +1220,52 @@ def delete_mfa_authenticator( return response + def get_mfa_challenge( + self, + user_id: str, + challenge_id: str + ) -> MfaChallengeSecret: + """ + Get a custom MFA challenge for a user, including the code to be delivered through your own channel. + + Parameters + ---------- + user_id : str + User ID. + challenge_id : str + ID of the challenge. + + Returns + ------- + MfaChallengeSecret + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/users/{userId}/mfa/challenges/{challengeId}' + api_params = {} + if user_id is None: + raise AppwriteException('Missing required parameter: "user_id"') + + if challenge_id is None: + raise AppwriteException('Missing required parameter: "challenge_id"') + + api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) + api_path = api_path.replace('{challengeId}', str(self._normalize_value(challenge_id))) + + + response = self.client.call('get', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=MfaChallengeSecret) + + def list_mfa_factors( self, user_id: str diff --git a/docs/examples/activities/list-events.md b/docs/examples/activities/list-events.md index bbeb644b..17f3b67d 100644 --- a/docs/examples/activities/list-events.md +++ b/docs/examples/activities/list-events.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key activities = Activities(client) result: ActivityEventList = activities.list_events( - queries = '' # optional + queries = [] # optional ) print(result.model_dump()) diff --git a/docs/examples/apps/create-installation-token.md b/docs/examples/apps/create-installation-token.md index 62a62ca6..acbe6cc7 100644 --- a/docs/examples/apps/create-installation-token.md +++ b/docs/examples/apps/create-installation-token.md @@ -6,7 +6,7 @@ from appwrite.models import Oauth2Token client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID -client.set_key('') # Your secret API key +client.set_session('') # The user session to authenticate with apps = Apps(client) diff --git a/docs/examples/account/create-jwt.md b/docs/examples/apps/delete-installation.md similarity index 58% rename from docs/examples/account/create-jwt.md rename to docs/examples/apps/delete-installation.md index a28c65fd..2a941e8e 100644 --- a/docs/examples/account/create-jwt.md +++ b/docs/examples/apps/delete-installation.md @@ -1,18 +1,16 @@ ```python from appwrite.client import Client -from appwrite.services.account import Account -from appwrite.models import Jwt +from appwrite.services.apps import Apps client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID client.set_session('') # The user session to authenticate with -account = Account(client) +apps = Apps(client) -result: Jwt = account.create_jwt( - duration = 0 # optional +result = apps.delete_installation( + app_id = '', + installation_id = '' ) - -print(result.model_dump()) ``` diff --git a/docs/examples/apps/get-installation.md b/docs/examples/apps/get-installation.md index f6a52721..d71858c9 100644 --- a/docs/examples/apps/get-installation.md +++ b/docs/examples/apps/get-installation.md @@ -6,7 +6,7 @@ from appwrite.models import AppInstallation client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID -client.set_key('') # Your secret API key +client.set_session('') # The user session to authenticate with apps = Apps(client) diff --git a/docs/examples/apps/list-installations.md b/docs/examples/apps/list-installations.md index f5e292b2..e21575cb 100644 --- a/docs/examples/apps/list-installations.md +++ b/docs/examples/apps/list-installations.md @@ -6,7 +6,7 @@ from appwrite.models import AppInstallationList client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint client.set_project('') # Your project ID -client.set_key('') # Your secret API key +client.set_session('') # The user session to authenticate with apps = Apps(client) diff --git a/docs/examples/embeddings/create-text-embeddings.md b/docs/examples/embeddings/create-text-embeddings.md new file mode 100644 index 00000000..49d3c258 --- /dev/null +++ b/docs/examples/embeddings/create-text-embeddings.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.embeddings import Embeddings +from appwrite.models import EmbeddingList +from appwrite.enums import EmbeddingModel + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +embeddings = Embeddings(client) + +result: EmbeddingList = embeddings.create_text_embeddings( + texts = [], + model = EmbeddingModel.NOMIC_EMBED_TEXT # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/project/get-policy.md b/docs/examples/project/get-policy.md index f9487669..16caef14 100644 --- a/docs/examples/project/get-policy.md +++ b/docs/examples/project/get-policy.md @@ -11,6 +11,7 @@ from appwrite.models import PolicySessionInvalidation from appwrite.models import PolicySessionLimit from appwrite.models import PolicyUserLimit from appwrite.models import PolicyMembershipPrivacy +from appwrite.models import PolicyMfaFactors from appwrite.models import PolicyDenyAliasedEmail from appwrite.models import PolicyDenyDisposableEmail from appwrite.models import PolicyDenyFreeEmail @@ -25,7 +26,7 @@ client.set_key('') # Your secret API key project = Project(client) -result: Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail] = project.get_policy( +result: Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail] = project.get_policy( policy_id = ProjectPolicyId.PASSWORD_DICTIONARY ) diff --git a/docs/examples/project/create-key.md b/docs/examples/project/update-mfa-factors-policy.md similarity index 58% rename from docs/examples/project/create-key.md rename to docs/examples/project/update-mfa-factors-policy.md index a3e040f7..67f75688 100644 --- a/docs/examples/project/create-key.md +++ b/docs/examples/project/update-mfa-factors-policy.md @@ -1,8 +1,7 @@ ```python from appwrite.client import Client from appwrite.services.project import Project -from appwrite.models import Key -from appwrite.enums import ProjectKeyScopes +from appwrite.models import Project as ProjectModel client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint @@ -11,11 +10,11 @@ client.set_key('') # Your secret API key project = Project(client) -result: Key = project.create_key( - key_id = '', - name = '', - scopes = [ProjectKeyScopes.PROJECT_READ], - expire = '2020-10-15T06:38:00.000+00:00' # optional +result: ProjectModel = project.update_mfa_factors_policy( + totp = False, # optional + email = False, # optional + phone = False, # optional + custom = False # optional ) print(result.model_dump()) diff --git a/docs/examples/project/update-o-auth-2-server.md b/docs/examples/project/update-o-auth-2-server.md index bce0876e..338ebf33 100644 --- a/docs/examples/project/update-o-auth-2-server.md +++ b/docs/examples/project/update-o-auth-2-server.md @@ -25,7 +25,8 @@ result: ProjectModel = project.update_o_auth2_server( user_code_length = 6, # optional user_code_format = 'numeric', # optional device_code_duration = 60, # optional - default_scopes = [] # optional + default_scopes = [], # optional + installation_scopes = [] # optional ) print(result.model_dump()) diff --git a/docs/examples/project/update-session-duration-policy.md b/docs/examples/project/update-session-duration-policy.md index 768bd4ff..817947e4 100644 --- a/docs/examples/project/update-session-duration-policy.md +++ b/docs/examples/project/update-session-duration-policy.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key project = Project(client) result: ProjectModel = project.update_session_duration_policy( - duration = 5 + duration = 60 ) print(result.model_dump()) diff --git a/docs/examples/project/update-user-limit-policy.md b/docs/examples/project/update-user-limit-policy.md index e841acae..42d66de3 100644 --- a/docs/examples/project/update-user-limit-policy.md +++ b/docs/examples/project/update-user-limit-policy.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key project = Project(client) result: ProjectModel = project.update_user_limit_policy( - total = 1 + total = 0 ) print(result.model_dump()) diff --git a/docs/examples/proxy/create-invalidation.md b/docs/examples/proxy/create-invalidation.md new file mode 100644 index 00000000..f94b4168 --- /dev/null +++ b/docs/examples/proxy/create-invalidation.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.proxy import Proxy +from appwrite.models import ProxyInvalidation +from appwrite.enums import InvalidationType + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +proxy = Proxy(client) + +result: ProxyInvalidation = proxy.create_invalidation( + domain = '', + type = InvalidationType.TAG, + reference = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/storage/create-file.md b/docs/examples/storage/create-file.md index 2103a1d6..cfec75c1 100644 --- a/docs/examples/storage/create-file.md +++ b/docs/examples/storage/create-file.md @@ -17,7 +17,8 @@ result: File = storage.create_file( bucket_id = '', file_id = '', file = InputFile.from_path('file.png'), - permissions = [Permission.read(Role.any())] # optional + permissions = [Permission.read(Role.any())], # optional + folder = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/create-migration.md b/docs/examples/tablesdb/create-migration.md new file mode 100644 index 00000000..46dd29bc --- /dev/null +++ b/docs/examples/tablesdb/create-migration.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DatabaseMigration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DatabaseMigration = tables_db.create_migration( + database_id = '', + specification = 's-1vcpu-1gb', + auto_cutover = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/create.md b/docs/examples/tablesdb/create.md index 0c5260cf..ca668875 100644 --- a/docs/examples/tablesdb/create.md +++ b/docs/examples/tablesdb/create.md @@ -15,7 +15,8 @@ result: Database = tables_db.create( name = '', enabled = False, # optional specification = 'serverless', # optional - replicas = 0 # optional + replicas = 0, # optional + sync_mode = 'async' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/cutover-migration.md b/docs/examples/tablesdb/cutover-migration.md new file mode 100644 index 00000000..1b793d63 --- /dev/null +++ b/docs/examples/tablesdb/cutover-migration.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DatabaseMigration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DatabaseMigration = tables_db.cutover_migration( + database_id = '', + migration_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/delete-migration.md b/docs/examples/tablesdb/delete-migration.md new file mode 100644 index 00000000..9442ae34 --- /dev/null +++ b/docs/examples/tablesdb/delete-migration.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result = tables_db.delete_migration( + database_id = '', + migration_id = '' +) +``` diff --git a/docs/examples/tablesdb/get-migration.md b/docs/examples/tablesdb/get-migration.md new file mode 100644 index 00000000..2efe0b63 --- /dev/null +++ b/docs/examples/tablesdb/get-migration.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DatabaseMigration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DatabaseMigration = tables_db.get_migration( + database_id = '', + migration_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/list-migrations.md b/docs/examples/tablesdb/list-migrations.md new file mode 100644 index 00000000..99665efa --- /dev/null +++ b/docs/examples/tablesdb/list-migrations.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DatabaseMigrationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DatabaseMigrationList = tables_db.list_migrations( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/list-operations.md b/docs/examples/tablesdb/list-operations.md new file mode 100644 index 00000000..afe14338 --- /dev/null +++ b/docs/examples/tablesdb/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.tables_db import TablesDB +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +tables_db = TablesDB(client) + +result: DedicatedDatabaseOperationList = tables_db.list_operations( + database_id = '', + status = 'running', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/tablesdb/update.md b/docs/examples/tablesdb/update.md index 8609072e..7fc0c930 100644 --- a/docs/examples/tablesdb/update.md +++ b/docs/examples/tablesdb/update.md @@ -14,7 +14,9 @@ result: Database = tables_db.update( database_id = '', name = '', # optional enabled = False, # optional - replicas = 0 # optional + specification = 'serverless', # optional + replicas = 0, # optional + sync_mode = 'async' # optional ) print(result.model_dump()) diff --git a/docs/examples/users/get-mfa-challenge.md b/docs/examples/users/get-mfa-challenge.md new file mode 100644 index 00000000..8dde75a7 --- /dev/null +++ b/docs/examples/users/get-mfa-challenge.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.users import Users +from appwrite.models import MfaChallengeSecret + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +users = Users(client) + +result: MfaChallengeSecret = users.get_mfa_challenge( + user_id = '', + challenge_id = '' +) + +print(result.model_dump()) +``` diff --git a/pyproject.toml b/pyproject.toml index b71d5337..f01bffcd 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "22.2.0" +version = "23.0.0" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" diff --git a/setup.py b/setup.py index 3d51ebff..980aaf26 100644 --- a/setup.py +++ b/setup.py @@ -8,7 +8,7 @@ setuptools.setup( name = 'appwrite', packages = setuptools.find_packages(), - version = '22.2.0', + version = '23.0.0', license='BSD-3-Clause', description = 'Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', long_description = long_description, @@ -18,7 +18,7 @@ maintainer = 'Appwrite Team', maintainer_email = 'team@appwrite.io', url = 'https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/22.2.0.tar.gz', + download_url='https://github.com/appwrite/sdk-for-python/archive/23.0.0.tar.gz', install_requires=[ 'requests', 'pydantic>=2,<3', diff --git a/test/services/test_account.py b/test/services/test_account.py index c0bab652..648aba16 100644 --- a/test/services/test_account.py +++ b/test/services/test_account.py @@ -230,19 +230,6 @@ def test_delete_identity(self, m): self.assertEqual(response, data) - @requests_mock.Mocker() - def test_create_jwt(self, m): - data = { - "jwt": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.create_jwt( - ) - - self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() def test_list_logs(self, m): data = { @@ -526,7 +513,8 @@ def test_list_mfa_factors(self, m): "totp": True, "phone": True, "email": True, - "recoveryCode": True + "recoveryCode": True, + "custom": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -542,7 +530,8 @@ def test_list_mfa_factors(self, m): "totp": True, "phone": True, "email": True, - "recoveryCode": True + "recoveryCode": True, + "custom": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -727,7 +716,6 @@ def test_get_prefs(self, m): response = self.account.get_prefs( ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() diff --git a/test/services/test_apps.py b/test/services/test_apps.py index e923f2e5..8f9145a3 100644 --- a/test/services/test_apps.py +++ b/test/services/test_apps.py @@ -225,6 +225,19 @@ def test_get_installation(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_delete_installation(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.apps.delete_installation( + '', + '', + ) + + self.assertEqual(response, data) + @requests_mock.Mocker() def test_create_installation_token(self, m): data = { diff --git a/test/services/test_embeddings.py b/test/services/test_embeddings.py new file mode 100644 index 00000000..8d2cf848 --- /dev/null +++ b/test/services/test_embeddings.py @@ -0,0 +1,30 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.embeddings import Embeddings + +class EmbeddingsServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.embeddings = Embeddings(self.client) + + @requests_mock.Mocker() + def test_create_text_embeddings(self, m): + data = { + "total": 5.0, + "embeddings": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.embeddings.create_text_embeddings( + [], + ) + + self.assertEqual(response.to_dict(), data) + diff --git a/test/services/test_organization.py b/test/services/test_organization.py index 544d647d..2bf4dbc8 100644 --- a/test/services/test_organization.py +++ b/test/services/test_organization.py @@ -22,7 +22,6 @@ def test_get(self, m): "name": "VIP", "total": 7.0, "prefs": {}, - "billingBudget": 50.0, "budgetAlerts": [], "billingPlan": "tier-1", "billingPlanId": "tier-1", @@ -37,7 +36,6 @@ def test_get(self, m): "storage": 25.0, "imageTransformations": 100.0, "screenshotsGenerated": 50.0, - "members": 25.0, "webhooks": 25.0, "wafRules": 2.0, "projects": 2.0, @@ -61,7 +59,6 @@ def test_get(self, m): "topics": 1.0, "authPhone": 10.0, "domains": 5.0, - "activityLogs": 7.0, "usageLogs": 30.0, "projectInactivityDays": 7.0, "alertLimit": 80.0, @@ -82,14 +79,6 @@ def test_get(self, m): "value": 25.0, "invoiceDesc": "" }, - "member": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, "realtime": { "name": "", "unit": "GB", @@ -106,14 +95,6 @@ def test_get(self, m): "value": 25.0, "invoiceDesc": "" }, - "realtimeBandwidth": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, "storage": { "name": "", "unit": "GB", @@ -145,38 +126,9 @@ def test_get(self, m): "price": 5, "value": 25.0, "invoiceDesc": "" - }, - "credits": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - } - }, - "addons": { - "seats": { - "supported": True, - "planIncluded": 1.0, - "limit": 5.0, - "type": "numeric", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "projects": { - "supported": True, - "planIncluded": 1.0, - "limit": 5.0, - "type": "numeric", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" } }, + "addons": {}, "budgetCapEnabled": True, "customSmtp": True, "emailBranding": True, @@ -194,14 +146,12 @@ def test_get(self, m): "supportsFreeEmailValidation": True, "supportsCorporateEmailValidation": True, "supportsProjectSpecificRoles": True, - "backupsEnabled": True, "usagePerProject": True, "supportedAddons": { "baa": True, "premiumGeoDB": True, "premiumGeoDBOrg": True }, - "backupPolicies": 1.0, "deploymentSize": 30.0, "buildSize": 2000.0, "databasesAllowEncrypt": True, @@ -211,22 +161,11 @@ def test_get(self, m): "billingStartDate": "2020-10-15T06:38:00.000+00:00", "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingTrialStartDate": "2020-10-15T06:38:00.000+00:00", "billingTrialDays": 14.0, "billingAggregationId": "adbc3de4rddfsd", "billingInvoiceId": "adbc3de4rddfsd", "paymentMethodId": "adbc3de4rddfsd", - "billingAddressId": "adbc3de4rddfsd", - "backupPaymentMethodId": "adbc3de4rddfsd", "status": "active", - "remarks": "Pending initial payment", - "agreementBAA": "", - "programManagerName": "", - "programManagerCalendar": "", - "programDiscordChannelName": "", - "programDiscordChannelUrl": "", - "billingPlanDowngrade": "tier-1", - "billingTaxId": "", "markedForDeletion": True, "platform": "imagine", "projects": [] @@ -248,7 +187,6 @@ def test_update(self, m): "name": "VIP", "total": 7.0, "prefs": {}, - "billingBudget": 50.0, "budgetAlerts": [], "billingPlan": "tier-1", "billingPlanId": "tier-1", @@ -263,7 +201,6 @@ def test_update(self, m): "storage": 25.0, "imageTransformations": 100.0, "screenshotsGenerated": 50.0, - "members": 25.0, "webhooks": 25.0, "wafRules": 2.0, "projects": 2.0, @@ -287,7 +224,6 @@ def test_update(self, m): "topics": 1.0, "authPhone": 10.0, "domains": 5.0, - "activityLogs": 7.0, "usageLogs": 30.0, "projectInactivityDays": 7.0, "alertLimit": 80.0, @@ -308,14 +244,6 @@ def test_update(self, m): "value": 25.0, "invoiceDesc": "" }, - "member": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, "realtime": { "name": "", "unit": "GB", @@ -332,14 +260,6 @@ def test_update(self, m): "value": 25.0, "invoiceDesc": "" }, - "realtimeBandwidth": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, "storage": { "name": "", "unit": "GB", @@ -371,38 +291,9 @@ def test_update(self, m): "price": 5, "value": 25.0, "invoiceDesc": "" - }, - "credits": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - } - }, - "addons": { - "seats": { - "supported": True, - "planIncluded": 1.0, - "limit": 5.0, - "type": "numeric", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "projects": { - "supported": True, - "planIncluded": 1.0, - "limit": 5.0, - "type": "numeric", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" } }, + "addons": {}, "budgetCapEnabled": True, "customSmtp": True, "emailBranding": True, @@ -420,14 +311,12 @@ def test_update(self, m): "supportsFreeEmailValidation": True, "supportsCorporateEmailValidation": True, "supportsProjectSpecificRoles": True, - "backupsEnabled": True, "usagePerProject": True, "supportedAddons": { "baa": True, "premiumGeoDB": True, "premiumGeoDBOrg": True }, - "backupPolicies": 1.0, "deploymentSize": 30.0, "buildSize": 2000.0, "databasesAllowEncrypt": True, @@ -437,22 +326,11 @@ def test_update(self, m): "billingStartDate": "2020-10-15T06:38:00.000+00:00", "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingTrialStartDate": "2020-10-15T06:38:00.000+00:00", "billingTrialDays": 14.0, "billingAggregationId": "adbc3de4rddfsd", "billingInvoiceId": "adbc3de4rddfsd", "paymentMethodId": "adbc3de4rddfsd", - "billingAddressId": "adbc3de4rddfsd", - "backupPaymentMethodId": "adbc3de4rddfsd", "status": "active", - "remarks": "Pending initial payment", - "agreementBAA": "", - "programManagerName": "", - "programManagerCalendar": "", - "programDiscordChannelName": "", - "programDiscordChannelUrl": "", - "billingPlanDowngrade": "tier-1", - "billingTaxId": "", "markedForDeletion": True, "platform": "imagine", "projects": [] diff --git a/test/services/test_project.py b/test/services/test_project.py index b4b9c640..9f8f36e0 100644 --- a/test/services/test_project.py +++ b/test/services/test_project.py @@ -120,30 +120,6 @@ def test_list_keys(self, m): self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() - def test_create_key(self, m): - data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.create_key( - '', - '', - [], - ) - - self.assertEqual(response.to_dict(), data) - @requests_mock.Mocker() def test_create_ephemeral_key(self, m): data = { @@ -1596,6 +1572,46 @@ def test_update_membership_privacy_policy(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_update_mfa_factors_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + "wafEnabled": True +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.project.update_mfa_factors_policy( + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_update_password_dictionary_policy(self, m): data = { diff --git a/test/services/test_proxy.py b/test/services/test_proxy.py index 5da8c18c..0891cc85 100644 --- a/test/services/test_proxy.py +++ b/test/services/test_proxy.py @@ -13,6 +13,24 @@ def setUp(self): self.client = Client() self.proxy = Proxy(self.client) + @requests_mock.Mocker() + def test_create_invalidation(self, m): + data = { + "domain": "appwrite.company.com", + "type": "tag", + "reference": "products", + "status": "success" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.proxy.create_invalidation( + '', + 'tag', + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_rules(self, m): data = { diff --git a/test/services/test_storage.py b/test/services/test_storage.py index 08ca786e..af4587cb 100644 --- a/test/services/test_storage.py +++ b/test/services/test_storage.py @@ -146,6 +146,8 @@ def test_create_file(self, m): "$updatedAt": "2020-10-15T06:38:00.000+00:00", "$permissions": [], "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", "signature": "5d529fd02b544198ae075bd57c1762bb", "mimeType": "image\/png", "sizeOriginal": 17890.0, @@ -175,6 +177,8 @@ def test_get_file(self, m): "$updatedAt": "2020-10-15T06:38:00.000+00:00", "$permissions": [], "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", "signature": "5d529fd02b544198ae075bd57c1762bb", "mimeType": "image\/png", "sizeOriginal": 17890.0, @@ -203,6 +207,8 @@ def test_update_file(self, m): "$updatedAt": "2020-10-15T06:38:00.000+00:00", "$permissions": [], "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", "signature": "5d529fd02b544198ae075bd57c1762bb", "mimeType": "image\/png", "sizeOriginal": 17890.0, diff --git a/test/services/test_tables_db.py b/test/services/test_tables_db.py index 888be71f..ba339712 100644 --- a/test/services/test_tables_db.py +++ b/test/services/test_tables_db.py @@ -56,7 +56,6 @@ def test_list_specifications(self, m): "storageOverageRate": 0.125, "bandwidthOverageRate": 0.08, "replicaRate": 1, - "crossRegionReplicaRate": 1, "pitrRate": 0.2 } } @@ -250,7 +249,6 @@ def test_create_failover(self, m): "nodePool": "db-pool-4vcpu-8gb", "replicas": 2.0, "syncMode": "async", - "crossRegionReplicas": 1.0, "networkMaxConnections": 500.0, "networkIdleTimeoutSeconds": 900.0, "networkIPAllowlist": [], @@ -279,11 +277,147 @@ def test_create_failover(self, m): self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_list_migrations(self, m): + data = { + "total": 5.0, + "migrations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.list_migrations( + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.create_migration( + '', + 's-1vcpu-1gb', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.get_migration( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_migration(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.delete_migration( + '', + '', + ) + + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_cutover_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.cutover_migration( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.tables_db.list_operations( + '', + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_get_replicas(self, m): data = { "replicas": 2.0, "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, "members": [] } headers = {'Content-Type': 'application/json'} @@ -307,6 +441,10 @@ def test_get_status(self, m): "current": 12.0, "max": 100.0 }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, "replicas": [], "volumes": [] } diff --git a/test/services/test_teams.py b/test/services/test_teams.py index 684d00f8..9c2635f5 100644 --- a/test/services/test_teams.py +++ b/test/services/test_teams.py @@ -352,7 +352,6 @@ def test_get_prefs(self, m): '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() @@ -366,6 +365,5 @@ def test_update_prefs(self, m): {}, ) - data['data'] = {} self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_users.py b/test/services/test_users.py index cd4eb71f..efb2130d 100644 --- a/test/services/test_users.py +++ b/test/services/test_users.py @@ -568,13 +568,33 @@ def test_delete_mfa_authenticator(self, m): self.assertEqual(response, data) + @requests_mock.Mocker() + def test_get_mfa_challenge(self, m): + data = { + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "expire": "2020-10-15T06:38:00.000+00:00", + "code": "446372" +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.users.get_mfa_challenge( + '', + '', + ) + + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() def test_list_mfa_factors(self, m): data = { "totp": True, "phone": True, "email": True, - "recoveryCode": True + "recoveryCode": True, + "custom": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -591,7 +611,8 @@ def test_list_mfa_factors(self, m): "totp": True, "phone": True, "email": True, - "recoveryCode": True + "recoveryCode": True, + "custom": True } headers = {'Content-Type': 'application/json'} m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) @@ -786,7 +807,6 @@ def test_get_prefs(self, m): '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() @@ -800,7 +820,6 @@ def test_update_prefs(self, m): {}, ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() From a4d7671f3ae9afc7c46420c0a6652bf164b28d3e Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 14 Aug 2026 13:50:41 +0530 Subject: [PATCH 07/10] chore: update Python SDK to 23.0.0 --- CHANGELOG.md | 1 - appwrite/encoders/value_class_encoder.py | 4 -- appwrite/enums/embedding_model.py | 7 --- appwrite/models/__init__.py | 4 -- appwrite/models/embedding.py | 24 -------- appwrite/models/embedding_list.py | 19 ------ appwrite/services/embeddings.py | 58 ------------------- .../embeddings/create-text-embeddings.md | 20 ------- test/services/test_embeddings.py | 30 ---------- 9 files changed, 167 deletions(-) delete mode 100644 appwrite/enums/embedding_model.py delete mode 100644 appwrite/models/embedding.py delete mode 100644 appwrite/models/embedding_list.py delete mode 100644 appwrite/services/embeddings.py delete mode 100644 docs/examples/embeddings/create-text-embeddings.md delete mode 100644 test/services/test_embeddings.py diff --git a/CHANGELOG.md b/CHANGELOG.md index 52fb6a98..fcdb057d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,7 +5,6 @@ * Breaking: removed `account.createJWT`; use `users.createJWT` instead. A leaked JWT could mint further JWTs, letting a credential outlive its own expiry — a session cannot duplicate itself to live forever either * Breaking: removed `project.createKey`. A leaked key could mint further hidden keys, making a compromise far harder to contain and revoke * Breaking: `activities.listEvents` `queries` now takes an array instead of a string -* Added: `embeddings` service with `createTextEmbeddings`, plus the `EmbeddingModel` enum * Added: TablesDB migration methods `listMigrations`, `createMigration`, `getMigration`, `deleteMigration`, `cutoverMigration`, and `listOperations` * Added: `proxy.createInvalidation` for purging cached edge responses, plus the `InvalidationType` enum * Added: `apps.deleteInstallation` diff --git a/appwrite/encoders/value_class_encoder.py b/appwrite/encoders/value_class_encoder.py index ab46a105..3a70a3d0 100644 --- a/appwrite/encoders/value_class_encoder.py +++ b/appwrite/encoders/value_class_encoder.py @@ -15,7 +15,6 @@ from ..enums.relation_mutate import RelationMutate from ..enums.databases_index_type import DatabasesIndexType from ..enums.order_by import OrderBy -from ..enums.embedding_model import EmbeddingModel from ..enums.runtime import Runtime from ..enums.project_key_scopes import ProjectKeyScopes from ..enums.template_reference_type import TemplateReferenceType @@ -113,9 +112,6 @@ def default(self, o): if isinstance(o, OrderBy): return o.value - if isinstance(o, EmbeddingModel): - return o.value - if isinstance(o, Runtime): return o.value diff --git a/appwrite/enums/embedding_model.py b/appwrite/enums/embedding_model.py deleted file mode 100644 index 5bbf1cf9..00000000 --- a/appwrite/enums/embedding_model.py +++ /dev/null @@ -1,7 +0,0 @@ -from enum import Enum - -class EmbeddingModel(Enum): - NOMIC_EMBED_TEXT = "nomic-embed-text" - EMBEDDING_GEMMA = "embedding-gemma" - ALL_MINILM = "all-minilm" - BGE_SMALL = "bge-small" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 9b7d0ced..5d001968 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -43,11 +43,9 @@ from .target_list import TargetList from .transaction_list import TransactionList from .specification_list import SpecificationList -from .embedding_list import EmbeddingList from .insight_list import InsightList from .report_list import ReportList from .database import Database -from .embedding import Embedding from .collection import Collection from .attribute_list import AttributeList from .attribute_string import AttributeString @@ -325,11 +323,9 @@ 'TargetList', 'TransactionList', 'SpecificationList', - 'EmbeddingList', 'InsightList', 'ReportList', 'Database', - 'Embedding', 'Collection', 'AttributeList', 'AttributeString', diff --git a/appwrite/models/embedding.py b/appwrite/models/embedding.py deleted file mode 100644 index 9da9bab5..00000000 --- a/appwrite/models/embedding.py +++ /dev/null @@ -1,24 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel - -class Embedding(AppwriteModel): - """ - Embedding - - Attributes - ---------- - model : str - Embedding model used to generate embeddings. - dimension : float - Number of dimensions for each embedding vector. - embedding : List[Any] - Embedding vector values. If an error occurs, this will be an empty array. - error : str - Error message if embedding generation fails. Empty string if no error. - """ - model: str = Field(..., alias='model') - dimension: float = Field(..., alias='dimension') - embedding: List[Any] = Field(..., alias='embedding') - error: str = Field(..., alias='error') diff --git a/appwrite/models/embedding_list.py b/appwrite/models/embedding_list.py deleted file mode 100644 index d8f437e7..00000000 --- a/appwrite/models/embedding_list.py +++ /dev/null @@ -1,19 +0,0 @@ -from typing import Any, Dict, List, Optional, Union, cast -from pydantic import Field, PrivateAttr - -from .base_model import AppwriteModel -from .embedding import Embedding - -class EmbeddingList(AppwriteModel): - """ - Embedding list - - Attributes - ---------- - total : float - Total number of embeddings that matched your query. - embeddings : List[Embedding] - List of embeddings. - """ - total: float = Field(..., alias='total') - embeddings: List[Embedding] = Field(..., alias='embeddings') diff --git a/appwrite/services/embeddings.py b/appwrite/services/embeddings.py deleted file mode 100644 index 50848d06..00000000 --- a/appwrite/services/embeddings.py +++ /dev/null @@ -1,58 +0,0 @@ -from ..service import Service -from urllib.parse import quote -from typing import Any, Dict, List, Optional, Union -from ..exception import AppwriteException -from appwrite.utils.deprecated import deprecated -from ..enums.embedding_model import EmbeddingModel -from ..models.embedding_list import EmbeddingList - -class Embeddings(Service): - - def __init__(self, client) -> None: - super(Embeddings, self).__init__(client) - - def create_text_embeddings( - self, - texts: List[str], - model: Optional[EmbeddingModel] = None - ) -> EmbeddingList: - """ - Generate vector embeddings for an array of text using the selected embedding model. Use the returned vectors to power semantic search and similarity queries against your vector collections. - - - Parameters - ---------- - texts : List[str] - Array of text to generate embeddings. - model : Optional[EmbeddingModel] - The embedding model to use for generating vector embeddings. - - Returns - ------- - EmbeddingList - API response as a typed Pydantic model - - Raises - ------ - AppwriteException - If API request fails - """ - - api_path = '/embeddings/text' - api_params = {} - if texts is None: - raise AppwriteException('Missing required parameter: "texts"') - - - api_params['texts'] = self._normalize_value(texts) - if model is not None: - api_params['model'] = self._normalize_value(model) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) - - return self._parse_response(response, model=EmbeddingList) - diff --git a/docs/examples/embeddings/create-text-embeddings.md b/docs/examples/embeddings/create-text-embeddings.md deleted file mode 100644 index 49d3c258..00000000 --- a/docs/examples/embeddings/create-text-embeddings.md +++ /dev/null @@ -1,20 +0,0 @@ -```python -from appwrite.client import Client -from appwrite.services.embeddings import Embeddings -from appwrite.models import EmbeddingList -from appwrite.enums import EmbeddingModel - -client = Client() -client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint -client.set_project('') # Your project ID -client.set_key('') # Your secret API key - -embeddings = Embeddings(client) - -result: EmbeddingList = embeddings.create_text_embeddings( - texts = [], - model = EmbeddingModel.NOMIC_EMBED_TEXT # optional -) - -print(result.model_dump()) -``` diff --git a/test/services/test_embeddings.py b/test/services/test_embeddings.py deleted file mode 100644 index 8d2cf848..00000000 --- a/test/services/test_embeddings.py +++ /dev/null @@ -1,30 +0,0 @@ -import json -import requests_mock -import unittest - -from appwrite.client import Client -from appwrite.input_file import InputFile -from appwrite.models import * -from appwrite.services.embeddings import Embeddings - -class EmbeddingsServiceTest(unittest.TestCase): - - def setUp(self): - self.client = Client() - self.embeddings = Embeddings(self.client) - - @requests_mock.Mocker() - def test_create_text_embeddings(self, m): - data = { - "total": 5.0, - "embeddings": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.embeddings.create_text_embeddings( - [], - ) - - self.assertEqual(response.to_dict(), data) - From 62ea5b878b67c6b7266a5a54e6755d3f543f8698 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Fri, 14 Aug 2026 14:00:27 +0530 Subject: [PATCH 08/10] chore: update Python SDK to 23.0.0 --- CHANGELOG.md | 1 + appwrite/encoders/value_class_encoder.py | 4 ++ appwrite/enums/embedding_model.py | 7 +++ appwrite/models/__init__.py | 4 ++ appwrite/models/embedding.py | 24 ++++++++ appwrite/models/embedding_list.py | 19 ++++++ appwrite/services/embeddings.py | 58 +++++++++++++++++++ .../embeddings/create-text-embeddings.md | 20 +++++++ test/services/test_embeddings.py | 30 ++++++++++ 9 files changed, 167 insertions(+) create mode 100644 appwrite/enums/embedding_model.py create mode 100644 appwrite/models/embedding.py create mode 100644 appwrite/models/embedding_list.py create mode 100644 appwrite/services/embeddings.py create mode 100644 docs/examples/embeddings/create-text-embeddings.md create mode 100644 test/services/test_embeddings.py diff --git a/CHANGELOG.md b/CHANGELOG.md index fcdb057d..52fb6a98 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ * Breaking: removed `account.createJWT`; use `users.createJWT` instead. A leaked JWT could mint further JWTs, letting a credential outlive its own expiry — a session cannot duplicate itself to live forever either * Breaking: removed `project.createKey`. A leaked key could mint further hidden keys, making a compromise far harder to contain and revoke * Breaking: `activities.listEvents` `queries` now takes an array instead of a string +* Added: `embeddings` service with `createTextEmbeddings`, plus the `EmbeddingModel` enum * Added: TablesDB migration methods `listMigrations`, `createMigration`, `getMigration`, `deleteMigration`, `cutoverMigration`, and `listOperations` * Added: `proxy.createInvalidation` for purging cached edge responses, plus the `InvalidationType` enum * Added: `apps.deleteInstallation` diff --git a/appwrite/encoders/value_class_encoder.py b/appwrite/encoders/value_class_encoder.py index 3a70a3d0..ab46a105 100644 --- a/appwrite/encoders/value_class_encoder.py +++ b/appwrite/encoders/value_class_encoder.py @@ -15,6 +15,7 @@ from ..enums.relation_mutate import RelationMutate from ..enums.databases_index_type import DatabasesIndexType from ..enums.order_by import OrderBy +from ..enums.embedding_model import EmbeddingModel from ..enums.runtime import Runtime from ..enums.project_key_scopes import ProjectKeyScopes from ..enums.template_reference_type import TemplateReferenceType @@ -112,6 +113,9 @@ def default(self, o): if isinstance(o, OrderBy): return o.value + if isinstance(o, EmbeddingModel): + return o.value + if isinstance(o, Runtime): return o.value diff --git a/appwrite/enums/embedding_model.py b/appwrite/enums/embedding_model.py new file mode 100644 index 00000000..5bbf1cf9 --- /dev/null +++ b/appwrite/enums/embedding_model.py @@ -0,0 +1,7 @@ +from enum import Enum + +class EmbeddingModel(Enum): + NOMIC_EMBED_TEXT = "nomic-embed-text" + EMBEDDING_GEMMA = "embedding-gemma" + ALL_MINILM = "all-minilm" + BGE_SMALL = "bge-small" diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 5d001968..9b7d0ced 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -43,9 +43,11 @@ from .target_list import TargetList from .transaction_list import TransactionList from .specification_list import SpecificationList +from .embedding_list import EmbeddingList from .insight_list import InsightList from .report_list import ReportList from .database import Database +from .embedding import Embedding from .collection import Collection from .attribute_list import AttributeList from .attribute_string import AttributeString @@ -323,9 +325,11 @@ 'TargetList', 'TransactionList', 'SpecificationList', + 'EmbeddingList', 'InsightList', 'ReportList', 'Database', + 'Embedding', 'Collection', 'AttributeList', 'AttributeString', diff --git a/appwrite/models/embedding.py b/appwrite/models/embedding.py new file mode 100644 index 00000000..9da9bab5 --- /dev/null +++ b/appwrite/models/embedding.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + +class Embedding(AppwriteModel): + """ + Embedding + + Attributes + ---------- + model : str + Embedding model used to generate embeddings. + dimension : float + Number of dimensions for each embedding vector. + embedding : List[Any] + Embedding vector values. If an error occurs, this will be an empty array. + error : str + Error message if embedding generation fails. Empty string if no error. + """ + model: str = Field(..., alias='model') + dimension: float = Field(..., alias='dimension') + embedding: List[Any] = Field(..., alias='embedding') + error: str = Field(..., alias='error') diff --git a/appwrite/models/embedding_list.py b/appwrite/models/embedding_list.py new file mode 100644 index 00000000..d8f437e7 --- /dev/null +++ b/appwrite/models/embedding_list.py @@ -0,0 +1,19 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .embedding import Embedding + +class EmbeddingList(AppwriteModel): + """ + Embedding list + + Attributes + ---------- + total : float + Total number of embeddings that matched your query. + embeddings : List[Embedding] + List of embeddings. + """ + total: float = Field(..., alias='total') + embeddings: List[Embedding] = Field(..., alias='embeddings') diff --git a/appwrite/services/embeddings.py b/appwrite/services/embeddings.py new file mode 100644 index 00000000..50848d06 --- /dev/null +++ b/appwrite/services/embeddings.py @@ -0,0 +1,58 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..enums.embedding_model import EmbeddingModel +from ..models.embedding_list import EmbeddingList + +class Embeddings(Service): + + def __init__(self, client) -> None: + super(Embeddings, self).__init__(client) + + def create_text_embeddings( + self, + texts: List[str], + model: Optional[EmbeddingModel] = None + ) -> EmbeddingList: + """ + Generate vector embeddings for an array of text using the selected embedding model. Use the returned vectors to power semantic search and similarity queries against your vector collections. + + + Parameters + ---------- + texts : List[str] + Array of text to generate embeddings. + model : Optional[EmbeddingModel] + The embedding model to use for generating vector embeddings. + + Returns + ------- + EmbeddingList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/embeddings/text' + api_params = {} + if texts is None: + raise AppwriteException('Missing required parameter: "texts"') + + + api_params['texts'] = self._normalize_value(texts) + if model is not None: + api_params['model'] = self._normalize_value(model) + + response = self.client.call('post', api_path, { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, api_params) + + return self._parse_response(response, model=EmbeddingList) + diff --git a/docs/examples/embeddings/create-text-embeddings.md b/docs/examples/embeddings/create-text-embeddings.md new file mode 100644 index 00000000..49d3c258 --- /dev/null +++ b/docs/examples/embeddings/create-text-embeddings.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.embeddings import Embeddings +from appwrite.models import EmbeddingList +from appwrite.enums import EmbeddingModel + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +embeddings = Embeddings(client) + +result: EmbeddingList = embeddings.create_text_embeddings( + texts = [], + model = EmbeddingModel.NOMIC_EMBED_TEXT # optional +) + +print(result.model_dump()) +``` diff --git a/test/services/test_embeddings.py b/test/services/test_embeddings.py new file mode 100644 index 00000000..8d2cf848 --- /dev/null +++ b/test/services/test_embeddings.py @@ -0,0 +1,30 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.embeddings import Embeddings + +class EmbeddingsServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.embeddings = Embeddings(self.client) + + @requests_mock.Mocker() + def test_create_text_embeddings(self, m): + data = { + "total": 5.0, + "embeddings": [] +} + headers = {'Content-Type': 'application/json'} + m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) + + response = self.embeddings.create_text_embeddings( + [], + ) + + self.assertEqual(response.to_dict(), data) + From 9d651bc5c49997fd760d7a1c8ed887f0d155ecbb Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Thu, 27 Aug 2026 18:00:42 +0530 Subject: [PATCH 09/10] chore: update Python SDK to 23.1.0rc1 --- CHANGELOG.md | 14 + appwrite/__init__.py | 1 - appwrite/client.py | 93 +- appwrite/encoders/__init__.py | 1 - appwrite/encoders/value_class_encoder.py | 13 + appwrite/enums/__init__.py | 1 - appwrite/enums/adapter.py | 1 + appwrite/enums/attribute_status.py | 1 + appwrite/enums/authentication_factor.py | 1 + appwrite/enums/authenticator_type.py | 1 + appwrite/enums/backup_services.py | 1 + appwrite/enums/billing_plan_group.py | 1 + appwrite/enums/browser.py | 1 + appwrite/enums/browser_permission.py | 1 + appwrite/enums/browser_theme.py | 1 + appwrite/enums/build_runtime.py | 2 + appwrite/enums/column_status.py | 1 + appwrite/enums/compression.py | 1 + appwrite/enums/credit_card.py | 1 + appwrite/enums/database_status.py | 1 + appwrite/enums/database_type.py | 1 + appwrite/enums/databases_index_type.py | 1 + appwrite/enums/deployment_download_type.py | 1 + appwrite/enums/deployment_status.py | 1 + appwrite/enums/documents_db_index_type.py | 7 + appwrite/enums/embedding_model.py | 3 +- appwrite/enums/execution_method.py | 1 + appwrite/enums/execution_resource_type.py | 6 + appwrite/enums/execution_status.py | 1 + appwrite/enums/execution_trigger.py | 1 + appwrite/enums/flag.py | 1 + appwrite/enums/framework.py | 1 + appwrite/enums/image_format.py | 1 + appwrite/enums/image_gravity.py | 1 + appwrite/enums/index_status.py | 1 + appwrite/enums/invalidation_type.py | 1 + appwrite/enums/message_priority.py | 1 + appwrite/enums/message_status.py | 1 + appwrite/enums/messaging_provider_type.py | 1 + appwrite/enums/o_auth2_google_prompt.py | 1 + appwrite/enums/o_auth2_oidc_prompt.py | 1 + appwrite/enums/o_auth_provider.py | 2 + appwrite/enums/order_by.py | 1 + appwrite/enums/organization_key_scopes.py | 1 + appwrite/enums/password_hash.py | 1 + appwrite/enums/platform_type.py | 1 + appwrite/enums/project_auth_method_id.py | 1 + appwrite/enums/project_email_template_id.py | 1 + .../enums/project_email_template_locale.py | 1 + appwrite/enums/project_key_scopes.py | 16 +- .../enums/project_o_auth2_google_prompt.py | 1 + appwrite/enums/project_o_auth2_oidc_prompt.py | 1 + appwrite/enums/project_o_auth_provider_id.py | 2 + appwrite/enums/project_policy_id.py | 1 + appwrite/enums/project_protocol_id.py | 1 + appwrite/enums/project_service_id.py | 1 + appwrite/enums/project_smtp_secure.py | 1 + appwrite/enums/proxy_resource_type.py | 1 + .../proxy_rule_deployment_resource_type.py | 1 + appwrite/enums/proxy_rule_status.py | 1 + appwrite/enums/region.py | 1 + appwrite/enums/relation_mutate.py | 1 + appwrite/enums/relationship_type.py | 1 + appwrite/enums/runtime.py | 2 + appwrite/enums/smtp_encryption.py | 1 + appwrite/enums/status_code.py | 1 + appwrite/enums/tables_db_index_type.py | 1 + appwrite/enums/template_reference_type.py | 1 + appwrite/enums/timezone.py | 1 + appwrite/enums/vcs_reference_type.py | 1 + appwrite/enums/vectors_db_index_type.py | 10 + appwrite/exception.py | 4 +- appwrite/id.py | 5 +- appwrite/input_file.py | 5 +- appwrite/models/__init__.py | 38 + appwrite/models/activity_event.py | 2 + appwrite/models/activity_event_list.py | 2 + appwrite/models/additional_resource.py | 2 + appwrite/models/algo_argon2.py | 2 + appwrite/models/algo_bcrypt.py | 2 + appwrite/models/algo_md5.py | 2 + appwrite/models/algo_phpass.py | 2 + appwrite/models/algo_scrypt.py | 2 + appwrite/models/algo_scrypt_modified.py | 2 + appwrite/models/algo_sha.py | 2 + appwrite/models/app.py | 2 + appwrite/models/app_installation.py | 6 +- appwrite/models/app_installation_list.py | 2 + appwrite/models/app_key.py | 2 + appwrite/models/app_key_list.py | 2 + appwrite/models/app_scope.py | 2 + appwrite/models/app_scope_list.py | 2 + appwrite/models/app_secret.py | 2 + appwrite/models/app_secret_list.py | 2 + appwrite/models/app_secret_plaintext.py | 2 + appwrite/models/apps_list.py | 2 + appwrite/models/attribute_bigint.py | 2 + appwrite/models/attribute_boolean.py | 2 + appwrite/models/attribute_datetime.py | 2 + appwrite/models/attribute_email.py | 2 + appwrite/models/attribute_enum.py | 2 + appwrite/models/attribute_float.py | 2 + appwrite/models/attribute_integer.py | 2 + appwrite/models/attribute_ip.py | 2 + appwrite/models/attribute_line.py | 2 + appwrite/models/attribute_list.py | 25 +- appwrite/models/attribute_longtext.py | 2 + appwrite/models/attribute_mediumtext.py | 2 + appwrite/models/attribute_object.py | 39 + appwrite/models/attribute_point.py | 2 + appwrite/models/attribute_polygon.py | 2 + appwrite/models/attribute_relationship.py | 2 + appwrite/models/attribute_string.py | 2 + appwrite/models/attribute_text.py | 2 + appwrite/models/attribute_url.py | 2 + appwrite/models/attribute_varchar.py | 2 + appwrite/models/attribute_vector.py | 42 + appwrite/models/backup_archive.py | 2 + appwrite/models/backup_archive_list.py | 2 + appwrite/models/backup_policy.py | 2 + appwrite/models/backup_policy_list.py | 2 + appwrite/models/backup_restoration.py | 4 +- appwrite/models/backup_restoration_list.py | 2 + appwrite/models/base_model.py | 1 + appwrite/models/billing_limits.py | 2 + appwrite/models/billing_plan.py | 8 + appwrite/models/billing_plan_addon.py | 2 + appwrite/models/billing_plan_addon_details.py | 2 + .../billing_plan_dedicated_database_limits.py | 2 + appwrite/models/billing_plan_limits.py | 2 + .../models/billing_plan_supported_addons.py | 2 + appwrite/models/block.py | 2 + appwrite/models/bucket.py | 2 + appwrite/models/bucket_list.py | 2 + appwrite/models/collection.py | 25 +- appwrite/models/collection_list.py | 2 + appwrite/models/column_bigint.py | 2 + appwrite/models/column_boolean.py | 2 + appwrite/models/column_datetime.py | 2 + appwrite/models/column_email.py | 2 + appwrite/models/column_enum.py | 2 + appwrite/models/column_float.py | 2 + appwrite/models/column_index.py | 2 + appwrite/models/column_index_list.py | 2 + appwrite/models/column_integer.py | 2 + appwrite/models/column_ip.py | 2 + appwrite/models/column_line.py | 2 + appwrite/models/column_list.py | 25 +- appwrite/models/column_longtext.py | 2 + appwrite/models/column_mediumtext.py | 2 + appwrite/models/column_point.py | 2 + appwrite/models/column_polygon.py | 2 + appwrite/models/column_relationship.py | 2 + appwrite/models/column_string.py | 2 + appwrite/models/column_text.py | 2 + appwrite/models/column_url.py | 2 + appwrite/models/column_varchar.py | 2 + appwrite/models/continent.py | 2 + appwrite/models/continent_list.py | 2 + appwrite/models/country.py | 2 + appwrite/models/country_list.py | 2 + appwrite/models/currency.py | 2 + appwrite/models/currency_list.py | 2 + appwrite/models/database.py | 11 + appwrite/models/database_list.py | 2 + appwrite/models/database_migration.py | 5 + appwrite/models/database_migration_list.py | 2 + appwrite/models/database_status.py | 2 + .../models/database_status_connections.py | 2 + appwrite/models/database_status_replica.py | 7 +- appwrite/models/database_status_volume.py | 2 + appwrite/models/dedicated_database.py | 2 + appwrite/models/dedicated_database_backup.py | 65 + .../models/dedicated_database_backup_list.py | 21 + .../dedicated_database_backup_storage.py | 29 + appwrite/models/dedicated_database_branch.py | 50 + .../models/dedicated_database_branch_list.py | 21 + .../models/dedicated_database_execution.py | 33 + .../dedicated_database_execution_column.py | 20 + .../models/dedicated_database_extensions.py | 24 + appwrite/models/dedicated_database_list.py | 21 + appwrite/models/dedicated_database_member.py | 7 +- .../models/dedicated_database_operation.py | 4 +- .../dedicated_database_operation_list.py | 2 + .../models/dedicated_database_pitr_windows.py | 20 + appwrite/models/dedicated_database_pooler.py | 44 + .../models/dedicated_database_replicas.py | 2 + .../models/dedicated_database_restoration.py | 50 + .../dedicated_database_restoration_list.py | 21 + .../dedicated_database_specification.py | 2 + .../dedicated_database_specification_list.py | 2 + ...edicated_database_specification_pricing.py | 2 + appwrite/models/deployment.py | 2 + appwrite/models/deployment_list.py | 2 + appwrite/models/dev_key.py | 2 + appwrite/models/document.py | 12 +- appwrite/models/document_list.py | 7 +- appwrite/models/email_template.py | 2 + appwrite/models/email_template_list.py | 2 + appwrite/models/embedding.py | 2 + appwrite/models/embedding_list.py | 2 + appwrite/models/ephemeral_key.py | 2 + appwrite/models/execution.py | 22 +- appwrite/models/execution_list.py | 2 + appwrite/models/file.py | 2 + appwrite/models/file_list.py | 2 + appwrite/models/framework.py | 2 + appwrite/models/framework_adapter.py | 2 + appwrite/models/framework_list.py | 2 + appwrite/models/function.py | 2 + appwrite/models/function_list.py | 2 + appwrite/models/headers.py | 2 + appwrite/models/identity.py | 2 + appwrite/models/identity_list.py | 2 + appwrite/models/index.py | 2 + appwrite/models/index_list.py | 2 + appwrite/models/insight.py | 2 + appwrite/models/insight_cta.py | 2 + appwrite/models/insight_list.py | 2 + appwrite/models/jwt.py | 2 + appwrite/models/key.py | 2 + appwrite/models/key_list.py | 2 + appwrite/models/language.py | 2 + appwrite/models/language_list.py | 2 + appwrite/models/locale.py | 2 + appwrite/models/locale_code.py | 2 + appwrite/models/locale_code_list.py | 2 + appwrite/models/log.py | 2 + appwrite/models/log_list.py | 2 + appwrite/models/membership.py | 2 + appwrite/models/membership_list.py | 2 + appwrite/models/message.py | 2 + appwrite/models/message_list.py | 2 + appwrite/models/mfa_challenge.py | 2 + appwrite/models/mfa_challenge_secret.py | 2 + appwrite/models/mfa_factors.py | 2 + appwrite/models/mfa_recovery_codes.py | 2 + appwrite/models/mfa_type.py | 2 + appwrite/models/mock_number.py | 4 +- appwrite/models/mock_number_list.py | 2 + appwrite/models/o_auth2_amazon.py | 2 + appwrite/models/o_auth2_apple.py | 2 + appwrite/models/o_auth2_appwrite.py | 2 + appwrite/models/o_auth2_auth0.py | 2 + appwrite/models/o_auth2_authentik.py | 2 + appwrite/models/o_auth2_autodesk.py | 2 + appwrite/models/o_auth2_bitbucket.py | 2 + appwrite/models/o_auth2_bitly.py | 2 + appwrite/models/o_auth2_box.py | 2 + appwrite/models/o_auth2_dailymotion.py | 2 + appwrite/models/o_auth2_discord.py | 2 + appwrite/models/o_auth2_disqus.py | 2 + appwrite/models/o_auth2_dropbox.py | 2 + appwrite/models/o_auth2_etsy.py | 2 + appwrite/models/o_auth2_facebook.py | 2 + appwrite/models/o_auth2_figma.py | 2 + appwrite/models/o_auth2_fusion_auth.py | 2 + appwrite/models/o_auth2_github.py | 2 + appwrite/models/o_auth2_gitlab.py | 2 + appwrite/models/o_auth2_google.py | 2 + appwrite/models/o_auth2_hugging_face.py | 26 + appwrite/models/o_auth2_keycloak.py | 2 + appwrite/models/o_auth2_kick.py | 2 + appwrite/models/o_auth2_linkedin.py | 2 + appwrite/models/o_auth2_microsoft.py | 2 + appwrite/models/o_auth2_notion.py | 2 + appwrite/models/o_auth2_oidc.py | 2 + appwrite/models/o_auth2_okta.py | 2 + appwrite/models/o_auth2_paypal.py | 2 + appwrite/models/o_auth2_podio.py | 2 + appwrite/models/o_auth2_provider_list.py | 52 +- appwrite/models/o_auth2_salesforce.py | 2 + appwrite/models/o_auth2_slack.py | 2 + appwrite/models/o_auth2_spotify.py | 2 + appwrite/models/o_auth2_stripe.py | 2 + appwrite/models/o_auth2_tradeshift.py | 2 + appwrite/models/o_auth2_twitch.py | 2 + appwrite/models/o_auth2_word_press.py | 2 + appwrite/models/o_auth2_x.py | 2 + appwrite/models/o_auth2_yahoo.py | 2 + appwrite/models/o_auth2_yandex.py | 2 + appwrite/models/o_auth2_zoho.py | 2 + appwrite/models/o_auth2_zoom.py | 2 + appwrite/models/oauth2_approve.py | 2 + appwrite/models/oauth2_authorize.py | 2 + appwrite/models/oauth2_consent.py | 2 + appwrite/models/oauth2_consent_list.py | 2 + appwrite/models/oauth2_consent_token.py | 2 + appwrite/models/oauth2_consent_token_list.py | 2 + .../models/oauth2_device_authorization.py | 2 + appwrite/models/oauth2_grant.py | 2 + appwrite/models/oauth2_organization.py | 2 + appwrite/models/oauth2_organization_list.py | 2 + appwrite/models/oauth2_par.py | 2 + appwrite/models/oauth2_project.py | 2 + appwrite/models/oauth2_project_list.py | 2 + appwrite/models/oauth2_reject.py | 2 + appwrite/models/oauth2_token.py | 2 + appwrite/models/organization.py | 6 +- appwrite/models/phone.py | 2 + appwrite/models/phone_list.py | 2 + appwrite/models/platform_android.py | 2 + appwrite/models/platform_apple.py | 2 + appwrite/models/platform_linux.py | 2 + appwrite/models/platform_list.py | 12 +- appwrite/models/platform_web.py | 2 + appwrite/models/platform_windows.py | 2 + appwrite/models/policy_deny_aliased_email.py | 2 + .../models/policy_deny_corporate_email.py | 2 + .../models/policy_deny_disposable_email.py | 2 + appwrite/models/policy_deny_free_email.py | 2 + appwrite/models/policy_list.py | 22 +- appwrite/models/policy_membership_privacy.py | 2 + appwrite/models/policy_mfa_factors.py | 2 + appwrite/models/policy_password_dictionary.py | 2 + appwrite/models/policy_password_history.py | 2 + .../models/policy_password_personal_data.py | 2 + appwrite/models/policy_password_strength.py | 2 + appwrite/models/policy_session_alert.py | 2 + appwrite/models/policy_session_duration.py | 2 + .../models/policy_session_invalidation.py | 2 + appwrite/models/policy_session_limit.py | 2 + appwrite/models/policy_user_limit.py | 2 + appwrite/models/postgres_extension.py | 26 + appwrite/models/preferences.py | 2 + appwrite/models/presence.py | 2 + appwrite/models/presence_list.py | 2 + appwrite/models/program.py | 2 + appwrite/models/project.py | 26 +- appwrite/models/project_auth_method.py | 2 + appwrite/models/project_list.py | 2 + appwrite/models/project_protocol.py | 2 + appwrite/models/project_service.py | 2 + appwrite/models/provider.py | 2 + appwrite/models/provider_list.py | 2 + appwrite/models/proxy_invalidation.py | 2 + appwrite/models/proxy_rule.py | 7 +- appwrite/models/proxy_rule_list.py | 2 + appwrite/models/report.py | 2 + appwrite/models/report_list.py | 2 + appwrite/models/resource_token.py | 2 + appwrite/models/resource_token_list.py | 2 + appwrite/models/row.py | 12 +- appwrite/models/row_list.py | 7 +- appwrite/models/runtime.py | 2 + appwrite/models/runtime_list.py | 2 + appwrite/models/session.py | 2 + appwrite/models/session_list.py | 2 + appwrite/models/site.py | 5 + appwrite/models/site_list.py | 2 + appwrite/models/specification.py | 2 + appwrite/models/specification_list.py | 2 + appwrite/models/subscriber.py | 2 + appwrite/models/subscriber_list.py | 2 + appwrite/models/table.py | 25 +- appwrite/models/table_list.py | 2 + appwrite/models/target.py | 2 + appwrite/models/target_list.py | 2 + appwrite/models/team.py | 6 +- appwrite/models/team_list.py | 7 +- appwrite/models/token.py | 2 + appwrite/models/topic.py | 2 + appwrite/models/topic_list.py | 2 + appwrite/models/transaction.py | 2 + appwrite/models/transaction_list.py | 2 + appwrite/models/usage_billing_plan.py | 2 + appwrite/models/user.py | 18 +- appwrite/models/user_list.py | 7 +- appwrite/models/variable.py | 2 + appwrite/models/variable_list.py | 2 + appwrite/models/vectorsdb_collection.py | 61 + appwrite/models/vectorsdb_collection_list.py | 21 + appwrite/models/webhook.py | 2 + appwrite/models/webhook_list.py | 2 + appwrite/operator.py | 10 +- appwrite/query.py | 9 +- appwrite/role.py | 15 +- appwrite/service.py | 12 +- appwrite/services/__init__.py | 1 - appwrite/services/account.py | 1163 +++--- appwrite/services/activities.py | 43 +- appwrite/services/advisor.py | 111 +- appwrite/services/apps.py | 494 +-- appwrite/services/avatars.py | 266 +- appwrite/services/backups.py | 275 +- appwrite/services/databases.py | 1816 +++++----- appwrite/services/documents_db.py | 2097 +++++++++++ appwrite/services/embeddings.py | 25 +- appwrite/services/functions.py | 609 ++-- appwrite/services/graphql.py | 51 +- appwrite/services/locale.py | 155 +- appwrite/services/messaging.py | 1059 +++--- appwrite/services/mongo.py | 1692 +++++++++ appwrite/services/mysql.py | 1872 ++++++++++ appwrite/services/oauth2.py | 242 +- appwrite/services/organization.py | 505 +-- appwrite/services/postgresql.py | 2007 +++++++++++ appwrite/services/presences.py | 117 +- appwrite/services/project.py | 2420 +++++++------ appwrite/services/proxy.py | 218 +- appwrite/services/sites.py | 604 ++-- appwrite/services/storage.py | 304 +- appwrite/services/tables_db.py | 2035 +++++------ appwrite/services/teams.py | 436 +-- appwrite/services/tokens.py | 112 +- appwrite/services/users.py | 1071 +++--- appwrite/services/vectors_db.py | 2008 +++++++++++ appwrite/services/webhooks.py | 142 +- appwrite/utils/deprecated.py | 16 +- docs/examples/avatars/get-initials.md | 2 +- docs/examples/avatars/get-photo.md | 22 + .../databases/create-big-int-attribute.md | 8 +- .../databases/create-boolean-attribute.md | 2 +- .../databases/create-datetime-attribute.md | 2 +- .../databases/create-email-attribute.md | 2 +- .../databases/create-enum-attribute.md | 6 +- .../databases/create-float-attribute.md | 8 +- docs/examples/databases/create-index.md | 2 +- .../databases/create-integer-attribute.md | 8 +- .../examples/databases/create-ip-attribute.md | 4 +- .../databases/create-line-attribute.md | 2 +- .../databases/create-longtext-attribute.md | 4 +- .../databases/create-mediumtext-attribute.md | 4 +- .../databases/create-point-attribute.md | 2 +- .../databases/create-polygon-attribute.md | 2 +- .../create-relationship-attribute.md | 4 +- .../databases/create-string-attribute.md | 4 +- .../databases/create-text-attribute.md | 4 +- .../databases/create-url-attribute.md | 2 +- .../databases/create-varchar-attribute.md | 4 +- .../databases/decrement-document-attribute.md | 6 +- docs/examples/databases/delete-attribute.md | 2 +- docs/examples/databases/delete-index.md | 2 +- docs/examples/databases/get-attribute.md | 2 +- docs/examples/databases/get-index.md | 2 +- .../databases/increment-document-attribute.md | 6 +- .../databases/update-big-int-attribute.md | 10 +- .../databases/update-boolean-attribute.md | 4 +- .../databases/update-datetime-attribute.md | 4 +- .../databases/update-email-attribute.md | 4 +- .../databases/update-enum-attribute.md | 8 +- .../databases/update-float-attribute.md | 10 +- .../databases/update-integer-attribute.md | 10 +- .../examples/databases/update-ip-attribute.md | 6 +- .../databases/update-line-attribute.md | 4 +- .../databases/update-longtext-attribute.md | 6 +- .../databases/update-mediumtext-attribute.md | 6 +- .../databases/update-point-attribute.md | 4 +- .../databases/update-polygon-attribute.md | 4 +- .../update-relationship-attribute.md | 4 +- .../databases/update-string-attribute.md | 6 +- .../databases/update-text-attribute.md | 6 +- .../databases/update-url-attribute.md | 4 +- .../databases/update-varchar-attribute.md | 6 +- .../examples/documentsdb/create-collection.md | 27 + docs/examples/documentsdb/create-document.md | 30 + docs/examples/documentsdb/create-documents.md | 20 + docs/examples/documentsdb/create-failover.md | 19 + docs/examples/documentsdb/create-index.md | 26 + .../examples/documentsdb/create-operations.md | 29 + .../documentsdb/create-transaction.md | 18 + docs/examples/documentsdb/create.md | 23 + .../decrement-document-attribute.md | 24 + .../examples/documentsdb/delete-collection.md | 16 + docs/examples/documentsdb/delete-document.md | 18 + docs/examples/documentsdb/delete-documents.md | 21 + docs/examples/documentsdb/delete-index.md | 17 + .../documentsdb/delete-transaction.md | 15 + docs/examples/documentsdb/delete.md | 15 + docs/examples/documentsdb/get-collection.md | 19 + docs/examples/documentsdb/get-document.md | 22 + docs/examples/documentsdb/get-index.md | 20 + docs/examples/documentsdb/get-replicas.md | 18 + docs/examples/documentsdb/get-status.md | 18 + docs/examples/documentsdb/get-transaction.md | 18 + docs/examples/documentsdb/get.md | 18 + .../increment-document-attribute.md | 24 + docs/examples/documentsdb/list-collections.md | 21 + docs/examples/documentsdb/list-documents.md | 23 + docs/examples/documentsdb/list-indexes.md | 21 + docs/examples/documentsdb/list-operations.md | 21 + .../documentsdb/list-specifications.md | 16 + .../examples/documentsdb/list-transactions.md | 18 + docs/examples/documentsdb/list.md | 19 + .../examples/documentsdb/update-collection.md | 26 + docs/examples/documentsdb/update-document.md | 25 + docs/examples/documentsdb/update-documents.md | 22 + .../documentsdb/update-transaction.md | 20 + docs/examples/documentsdb/update.md | 23 + docs/examples/documentsdb/upsert-document.md | 25 + docs/examples/documentsdb/upsert-documents.md | 21 + docs/examples/functions/create.md | 6 +- docs/examples/functions/update.md | 6 +- .../messaging/create-mailgun-provider.md | 2 +- docs/examples/messaging/create-push.md | 2 +- .../messaging/create-smtp-provider.md | 2 +- .../messaging/update-mailgun-provider.md | 2 +- docs/examples/messaging/update-push.md | 2 +- docs/examples/mongo/create-backup-policy.md | 24 + docs/examples/mongo/create-backup.md | 19 + docs/examples/mongo/create-branch.md | 20 + docs/examples/mongo/create-failover.md | 19 + docs/examples/mongo/create-migration.md | 20 + docs/examples/mongo/create-restoration.md | 22 + docs/examples/mongo/create-upgrade.md | 19 + docs/examples/mongo/create.md | 31 + docs/examples/mongo/delete-backup-policy.md | 16 + docs/examples/mongo/delete-backup.md | 16 + docs/examples/mongo/delete-branch.md | 19 + docs/examples/mongo/delete.md | 15 + docs/examples/mongo/get-backup-policy.md | 19 + docs/examples/mongo/get-backup.md | 19 + docs/examples/mongo/get-pitr.md | 18 + docs/examples/mongo/get-replicas.md | 18 + docs/examples/mongo/get-restoration.md | 19 + docs/examples/mongo/get-status.md | 18 + docs/examples/mongo/get.md | 18 + docs/examples/mongo/list-backup-policies.md | 19 + docs/examples/mongo/list-backups.md | 19 + docs/examples/mongo/list-branches.md | 18 + docs/examples/mongo/list-operations.md | 21 + docs/examples/mongo/list-restorations.md | 22 + docs/examples/mongo/list-specifications.md | 16 + docs/examples/mongo/list.md | 18 + docs/examples/mongo/update-backup-policy.md | 23 + docs/examples/mongo/update-backup-storage.md | 25 + docs/examples/mongo/update-credentials.md | 18 + docs/examples/mongo/update-maintenance.md | 20 + docs/examples/mongo/update.md | 38 + docs/examples/mysql/create-backup-policy.md | 24 + docs/examples/mysql/create-backup.md | 19 + docs/examples/mysql/create-branch.md | 20 + docs/examples/mysql/create-execution.md | 21 + docs/examples/mysql/create-failover.md | 19 + docs/examples/mysql/create-migration.md | 20 + docs/examples/mysql/create-restoration.md | 22 + docs/examples/mysql/create-upgrade.md | 19 + docs/examples/mysql/create.md | 31 + docs/examples/mysql/delete-backup-policy.md | 16 + docs/examples/mysql/delete-backup.md | 16 + docs/examples/mysql/delete-branch.md | 19 + docs/examples/mysql/delete.md | 15 + docs/examples/mysql/get-backup-policy.md | 19 + docs/examples/mysql/get-backup.md | 19 + docs/examples/mysql/get-pitr.md | 18 + docs/examples/mysql/get-pooler.md | 18 + docs/examples/mysql/get-replicas.md | 18 + docs/examples/mysql/get-restoration.md | 19 + docs/examples/mysql/get-status.md | 18 + docs/examples/mysql/get.md | 18 + docs/examples/mysql/list-backup-policies.md | 19 + docs/examples/mysql/list-backups.md | 19 + docs/examples/mysql/list-branches.md | 18 + docs/examples/mysql/list-operations.md | 21 + docs/examples/mysql/list-restorations.md | 22 + docs/examples/mysql/list-specifications.md | 16 + docs/examples/mysql/list.md | 18 + docs/examples/mysql/update-backup-policy.md | 23 + docs/examples/mysql/update-backup-storage.md | 25 + docs/examples/mysql/update-credentials.md | 18 + docs/examples/mysql/update-maintenance.md | 20 + docs/examples/mysql/update-pooler.md | 26 + docs/examples/mysql/update.md | 38 + docs/examples/organization/create-project.md | 2 +- .../postgresql/create-backup-policy.md | 24 + docs/examples/postgresql/create-backup.md | 19 + docs/examples/postgresql/create-branch.md | 20 + docs/examples/postgresql/create-execution.md | 21 + docs/examples/postgresql/create-extension.md | 19 + docs/examples/postgresql/create-failover.md | 19 + docs/examples/postgresql/create-migration.md | 20 + .../examples/postgresql/create-restoration.md | 22 + docs/examples/postgresql/create-upgrade.md | 19 + docs/examples/postgresql/create.md | 31 + .../postgresql/delete-backup-policy.md | 16 + docs/examples/postgresql/delete-backup.md | 16 + docs/examples/postgresql/delete-branch.md | 19 + docs/examples/postgresql/delete-extension.md | 19 + docs/examples/postgresql/delete.md | 15 + docs/examples/postgresql/get-backup-policy.md | 19 + docs/examples/postgresql/get-backup.md | 19 + docs/examples/postgresql/get-pitr.md | 18 + docs/examples/postgresql/get-pooler.md | 18 + docs/examples/postgresql/get-replicas.md | 18 + docs/examples/postgresql/get-restoration.md | 19 + docs/examples/postgresql/get-status.md | 18 + docs/examples/postgresql/get.md | 18 + .../postgresql/list-backup-policies.md | 19 + docs/examples/postgresql/list-backups.md | 19 + docs/examples/postgresql/list-branches.md | 18 + docs/examples/postgresql/list-extensions.md | 18 + docs/examples/postgresql/list-operations.md | 21 + docs/examples/postgresql/list-restorations.md | 22 + .../postgresql/list-specifications.md | 16 + docs/examples/postgresql/list.md | 18 + .../postgresql/update-backup-policy.md | 23 + .../postgresql/update-backup-storage.md | 25 + .../examples/postgresql/update-credentials.md | 18 + .../examples/postgresql/update-maintenance.md | 20 + docs/examples/postgresql/update-pooler.md | 26 + docs/examples/postgresql/update.md | 38 + .../examples/project/get-o-auth-2-provider.md | 3 +- .../project/update-o-auth-2-hugging-face.md | 20 + docs/examples/project/update-o-auth-2-okta.md | 2 +- docs/examples/project/update-smtp.md | 4 +- docs/examples/proxy/create-api-rule.md | 2 +- docs/examples/proxy/create-function-rule.md | 2 +- docs/examples/proxy/create-invalidation.md | 2 +- docs/examples/proxy/create-redirect-rule.md | 2 +- docs/examples/proxy/create-site-rule.md | 2 +- docs/examples/sites/create.md | 8 +- docs/examples/sites/update.md | 8 +- docs/examples/storage/create-file.md | 2 +- docs/examples/storage/get-file-preview.md | 4 +- .../tablesdb/create-big-int-column.md | 8 +- .../tablesdb/create-boolean-column.md | 2 +- .../tablesdb/create-datetime-column.md | 2 +- docs/examples/tablesdb/create-email-column.md | 2 +- docs/examples/tablesdb/create-enum-column.md | 6 +- docs/examples/tablesdb/create-float-column.md | 8 +- docs/examples/tablesdb/create-index.md | 2 +- .../tablesdb/create-integer-column.md | 8 +- docs/examples/tablesdb/create-ip-column.md | 4 +- docs/examples/tablesdb/create-line-column.md | 2 +- .../tablesdb/create-longtext-column.md | 4 +- .../tablesdb/create-mediumtext-column.md | 4 +- docs/examples/tablesdb/create-point-column.md | 2 +- .../tablesdb/create-polygon-column.md | 2 +- .../tablesdb/create-relationship-column.md | 4 +- .../examples/tablesdb/create-string-column.md | 4 +- docs/examples/tablesdb/create-text-column.md | 4 +- docs/examples/tablesdb/create-url-column.md | 2 +- .../tablesdb/create-varchar-column.md | 4 +- .../examples/tablesdb/decrement-row-column.md | 6 +- docs/examples/tablesdb/delete-column.md | 2 +- docs/examples/tablesdb/delete-index.md | 2 +- docs/examples/tablesdb/get-column.md | 2 +- docs/examples/tablesdb/get-index.md | 2 +- .../examples/tablesdb/increment-row-column.md | 6 +- docs/examples/tablesdb/list-operations.md | 2 +- .../tablesdb/update-big-int-column.md | 10 +- .../tablesdb/update-boolean-column.md | 4 +- .../tablesdb/update-datetime-column.md | 4 +- docs/examples/tablesdb/update-email-column.md | 4 +- docs/examples/tablesdb/update-enum-column.md | 8 +- docs/examples/tablesdb/update-float-column.md | 10 +- .../tablesdb/update-integer-column.md | 10 +- docs/examples/tablesdb/update-ip-column.md | 6 +- docs/examples/tablesdb/update-line-column.md | 4 +- .../tablesdb/update-longtext-column.md | 6 +- .../tablesdb/update-mediumtext-column.md | 6 +- docs/examples/tablesdb/update-point-column.md | 4 +- .../tablesdb/update-polygon-column.md | 4 +- .../tablesdb/update-relationship-column.md | 4 +- .../examples/tablesdb/update-string-column.md | 6 +- docs/examples/tablesdb/update-text-column.md | 6 +- docs/examples/tablesdb/update-url-column.md | 4 +- .../tablesdb/update-varchar-column.md | 6 +- docs/examples/users/create-jwt.md | 2 +- docs/examples/users/create-scrypt-user.md | 8 +- docs/examples/vectorsdb/create-collection.md | 26 + docs/examples/vectorsdb/create-document.md | 34 + docs/examples/vectorsdb/create-documents.md | 20 + docs/examples/vectorsdb/create-failover.md | 19 + docs/examples/vectorsdb/create-index.md | 26 + docs/examples/vectorsdb/create-operations.md | 29 + docs/examples/vectorsdb/create-query.md | 23 + docs/examples/vectorsdb/create-transaction.md | 18 + docs/examples/vectorsdb/create.md | 23 + docs/examples/vectorsdb/delete-collection.md | 16 + docs/examples/vectorsdb/delete-document.md | 18 + docs/examples/vectorsdb/delete-documents.md | 21 + docs/examples/vectorsdb/delete-index.md | 17 + docs/examples/vectorsdb/delete-transaction.md | 15 + docs/examples/vectorsdb/delete.md | 15 + docs/examples/vectorsdb/get-collection.md | 19 + docs/examples/vectorsdb/get-document.md | 22 + docs/examples/vectorsdb/get-index.md | 20 + docs/examples/vectorsdb/get-replicas.md | 18 + docs/examples/vectorsdb/get-status.md | 18 + docs/examples/vectorsdb/get-transaction.md | 18 + docs/examples/vectorsdb/get.md | 18 + docs/examples/vectorsdb/list-collections.md | 21 + docs/examples/vectorsdb/list-documents.md | 23 + docs/examples/vectorsdb/list-indexes.md | 21 + docs/examples/vectorsdb/list-operations.md | 21 + .../examples/vectorsdb/list-specifications.md | 16 + docs/examples/vectorsdb/list-transactions.md | 18 + docs/examples/vectorsdb/list.md | 19 + docs/examples/vectorsdb/update-collection.md | 26 + docs/examples/vectorsdb/update-document.md | 25 + docs/examples/vectorsdb/update-documents.md | 22 + docs/examples/vectorsdb/update-transaction.md | 20 + docs/examples/vectorsdb/update.md | 23 + docs/examples/vectorsdb/upsert-document.md | 25 + docs/examples/vectorsdb/upsert-documents.md | 21 + docs/examples/webhooks/create.md | 2 +- docs/examples/webhooks/update.md | 2 +- pyproject.toml | 8 +- setup.py | 60 +- test/services/test_account.py | 1775 +++++----- test/services/test_activities.py | 87 +- test/services/test_advisor.py | 114 +- test/services/test_apps.py | 613 ++-- test/services/test_avatars.py | 86 +- test/services/test_backups.py | 289 +- test/services/test_databases.py | 1858 +++++----- test/services/test_documents_db.py | 874 +++++ test/services/test_embeddings.py | 17 +- test/services/test_functions.py | 1003 +++--- test/services/test_graphql.py | 20 +- test/services/test_locale.py | 140 +- test/services/test_messaging.py | 1407 ++++---- test/services/test_mongo.py | 1110 ++++++ test/services/test_mysql.py | 1185 +++++++ test/services/test_oauth2.py | 231 +- test/services/test_organization.py | 1244 +++---- test/services/test_postgresql.py | 1330 +++++++ test/services/test_presences.py | 96 +- test/services/test_project.py | 3125 +++++++++-------- test/services/test_proxy.py | 290 +- test/services/test_sites.py | 977 +++--- test/services/test_storage.py | 324 +- test/services/test_tables_db.py | 2234 ++++++------ test/services/test_teams.py | 413 ++- test/services/test_tokens.py | 101 +- test/services/test_users.py | 1362 +++---- test/services/test_vectors_db.py | 843 +++++ test/services/test_webhooks.py | 179 +- test/test_id.py | 1 + test/test_operator.py | 17 +- test/test_permission.py | 1 + test/test_query.py | 20 +- test/test_role.py | 1 + 734 files changed, 37860 insertions(+), 15506 deletions(-) create mode 100644 appwrite/enums/documents_db_index_type.py create mode 100644 appwrite/enums/execution_resource_type.py create mode 100644 appwrite/enums/vectors_db_index_type.py create mode 100644 appwrite/models/attribute_object.py create mode 100644 appwrite/models/attribute_vector.py create mode 100644 appwrite/models/dedicated_database_backup.py create mode 100644 appwrite/models/dedicated_database_backup_list.py create mode 100644 appwrite/models/dedicated_database_backup_storage.py create mode 100644 appwrite/models/dedicated_database_branch.py create mode 100644 appwrite/models/dedicated_database_branch_list.py create mode 100644 appwrite/models/dedicated_database_execution.py create mode 100644 appwrite/models/dedicated_database_execution_column.py create mode 100644 appwrite/models/dedicated_database_extensions.py create mode 100644 appwrite/models/dedicated_database_list.py create mode 100644 appwrite/models/dedicated_database_pitr_windows.py create mode 100644 appwrite/models/dedicated_database_pooler.py create mode 100644 appwrite/models/dedicated_database_restoration.py create mode 100644 appwrite/models/dedicated_database_restoration_list.py create mode 100644 appwrite/models/o_auth2_hugging_face.py create mode 100644 appwrite/models/postgres_extension.py create mode 100644 appwrite/models/vectorsdb_collection.py create mode 100644 appwrite/models/vectorsdb_collection_list.py create mode 100644 appwrite/services/documents_db.py create mode 100644 appwrite/services/mongo.py create mode 100644 appwrite/services/mysql.py create mode 100644 appwrite/services/postgresql.py create mode 100644 appwrite/services/vectors_db.py create mode 100644 docs/examples/avatars/get-photo.md create mode 100644 docs/examples/documentsdb/create-collection.md create mode 100644 docs/examples/documentsdb/create-document.md create mode 100644 docs/examples/documentsdb/create-documents.md create mode 100644 docs/examples/documentsdb/create-failover.md create mode 100644 docs/examples/documentsdb/create-index.md create mode 100644 docs/examples/documentsdb/create-operations.md create mode 100644 docs/examples/documentsdb/create-transaction.md create mode 100644 docs/examples/documentsdb/create.md create mode 100644 docs/examples/documentsdb/decrement-document-attribute.md create mode 100644 docs/examples/documentsdb/delete-collection.md create mode 100644 docs/examples/documentsdb/delete-document.md create mode 100644 docs/examples/documentsdb/delete-documents.md create mode 100644 docs/examples/documentsdb/delete-index.md create mode 100644 docs/examples/documentsdb/delete-transaction.md create mode 100644 docs/examples/documentsdb/delete.md create mode 100644 docs/examples/documentsdb/get-collection.md create mode 100644 docs/examples/documentsdb/get-document.md create mode 100644 docs/examples/documentsdb/get-index.md create mode 100644 docs/examples/documentsdb/get-replicas.md create mode 100644 docs/examples/documentsdb/get-status.md create mode 100644 docs/examples/documentsdb/get-transaction.md create mode 100644 docs/examples/documentsdb/get.md create mode 100644 docs/examples/documentsdb/increment-document-attribute.md create mode 100644 docs/examples/documentsdb/list-collections.md create mode 100644 docs/examples/documentsdb/list-documents.md create mode 100644 docs/examples/documentsdb/list-indexes.md create mode 100644 docs/examples/documentsdb/list-operations.md create mode 100644 docs/examples/documentsdb/list-specifications.md create mode 100644 docs/examples/documentsdb/list-transactions.md create mode 100644 docs/examples/documentsdb/list.md create mode 100644 docs/examples/documentsdb/update-collection.md create mode 100644 docs/examples/documentsdb/update-document.md create mode 100644 docs/examples/documentsdb/update-documents.md create mode 100644 docs/examples/documentsdb/update-transaction.md create mode 100644 docs/examples/documentsdb/update.md create mode 100644 docs/examples/documentsdb/upsert-document.md create mode 100644 docs/examples/documentsdb/upsert-documents.md create mode 100644 docs/examples/mongo/create-backup-policy.md create mode 100644 docs/examples/mongo/create-backup.md create mode 100644 docs/examples/mongo/create-branch.md create mode 100644 docs/examples/mongo/create-failover.md create mode 100644 docs/examples/mongo/create-migration.md create mode 100644 docs/examples/mongo/create-restoration.md create mode 100644 docs/examples/mongo/create-upgrade.md create mode 100644 docs/examples/mongo/create.md create mode 100644 docs/examples/mongo/delete-backup-policy.md create mode 100644 docs/examples/mongo/delete-backup.md create mode 100644 docs/examples/mongo/delete-branch.md create mode 100644 docs/examples/mongo/delete.md create mode 100644 docs/examples/mongo/get-backup-policy.md create mode 100644 docs/examples/mongo/get-backup.md create mode 100644 docs/examples/mongo/get-pitr.md create mode 100644 docs/examples/mongo/get-replicas.md create mode 100644 docs/examples/mongo/get-restoration.md create mode 100644 docs/examples/mongo/get-status.md create mode 100644 docs/examples/mongo/get.md create mode 100644 docs/examples/mongo/list-backup-policies.md create mode 100644 docs/examples/mongo/list-backups.md create mode 100644 docs/examples/mongo/list-branches.md create mode 100644 docs/examples/mongo/list-operations.md create mode 100644 docs/examples/mongo/list-restorations.md create mode 100644 docs/examples/mongo/list-specifications.md create mode 100644 docs/examples/mongo/list.md create mode 100644 docs/examples/mongo/update-backup-policy.md create mode 100644 docs/examples/mongo/update-backup-storage.md create mode 100644 docs/examples/mongo/update-credentials.md create mode 100644 docs/examples/mongo/update-maintenance.md create mode 100644 docs/examples/mongo/update.md create mode 100644 docs/examples/mysql/create-backup-policy.md create mode 100644 docs/examples/mysql/create-backup.md create mode 100644 docs/examples/mysql/create-branch.md create mode 100644 docs/examples/mysql/create-execution.md create mode 100644 docs/examples/mysql/create-failover.md create mode 100644 docs/examples/mysql/create-migration.md create mode 100644 docs/examples/mysql/create-restoration.md create mode 100644 docs/examples/mysql/create-upgrade.md create mode 100644 docs/examples/mysql/create.md create mode 100644 docs/examples/mysql/delete-backup-policy.md create mode 100644 docs/examples/mysql/delete-backup.md create mode 100644 docs/examples/mysql/delete-branch.md create mode 100644 docs/examples/mysql/delete.md create mode 100644 docs/examples/mysql/get-backup-policy.md create mode 100644 docs/examples/mysql/get-backup.md create mode 100644 docs/examples/mysql/get-pitr.md create mode 100644 docs/examples/mysql/get-pooler.md create mode 100644 docs/examples/mysql/get-replicas.md create mode 100644 docs/examples/mysql/get-restoration.md create mode 100644 docs/examples/mysql/get-status.md create mode 100644 docs/examples/mysql/get.md create mode 100644 docs/examples/mysql/list-backup-policies.md create mode 100644 docs/examples/mysql/list-backups.md create mode 100644 docs/examples/mysql/list-branches.md create mode 100644 docs/examples/mysql/list-operations.md create mode 100644 docs/examples/mysql/list-restorations.md create mode 100644 docs/examples/mysql/list-specifications.md create mode 100644 docs/examples/mysql/list.md create mode 100644 docs/examples/mysql/update-backup-policy.md create mode 100644 docs/examples/mysql/update-backup-storage.md create mode 100644 docs/examples/mysql/update-credentials.md create mode 100644 docs/examples/mysql/update-maintenance.md create mode 100644 docs/examples/mysql/update-pooler.md create mode 100644 docs/examples/mysql/update.md create mode 100644 docs/examples/postgresql/create-backup-policy.md create mode 100644 docs/examples/postgresql/create-backup.md create mode 100644 docs/examples/postgresql/create-branch.md create mode 100644 docs/examples/postgresql/create-execution.md create mode 100644 docs/examples/postgresql/create-extension.md create mode 100644 docs/examples/postgresql/create-failover.md create mode 100644 docs/examples/postgresql/create-migration.md create mode 100644 docs/examples/postgresql/create-restoration.md create mode 100644 docs/examples/postgresql/create-upgrade.md create mode 100644 docs/examples/postgresql/create.md create mode 100644 docs/examples/postgresql/delete-backup-policy.md create mode 100644 docs/examples/postgresql/delete-backup.md create mode 100644 docs/examples/postgresql/delete-branch.md create mode 100644 docs/examples/postgresql/delete-extension.md create mode 100644 docs/examples/postgresql/delete.md create mode 100644 docs/examples/postgresql/get-backup-policy.md create mode 100644 docs/examples/postgresql/get-backup.md create mode 100644 docs/examples/postgresql/get-pitr.md create mode 100644 docs/examples/postgresql/get-pooler.md create mode 100644 docs/examples/postgresql/get-replicas.md create mode 100644 docs/examples/postgresql/get-restoration.md create mode 100644 docs/examples/postgresql/get-status.md create mode 100644 docs/examples/postgresql/get.md create mode 100644 docs/examples/postgresql/list-backup-policies.md create mode 100644 docs/examples/postgresql/list-backups.md create mode 100644 docs/examples/postgresql/list-branches.md create mode 100644 docs/examples/postgresql/list-extensions.md create mode 100644 docs/examples/postgresql/list-operations.md create mode 100644 docs/examples/postgresql/list-restorations.md create mode 100644 docs/examples/postgresql/list-specifications.md create mode 100644 docs/examples/postgresql/list.md create mode 100644 docs/examples/postgresql/update-backup-policy.md create mode 100644 docs/examples/postgresql/update-backup-storage.md create mode 100644 docs/examples/postgresql/update-credentials.md create mode 100644 docs/examples/postgresql/update-maintenance.md create mode 100644 docs/examples/postgresql/update-pooler.md create mode 100644 docs/examples/postgresql/update.md create mode 100644 docs/examples/project/update-o-auth-2-hugging-face.md create mode 100644 docs/examples/vectorsdb/create-collection.md create mode 100644 docs/examples/vectorsdb/create-document.md create mode 100644 docs/examples/vectorsdb/create-documents.md create mode 100644 docs/examples/vectorsdb/create-failover.md create mode 100644 docs/examples/vectorsdb/create-index.md create mode 100644 docs/examples/vectorsdb/create-operations.md create mode 100644 docs/examples/vectorsdb/create-query.md create mode 100644 docs/examples/vectorsdb/create-transaction.md create mode 100644 docs/examples/vectorsdb/create.md create mode 100644 docs/examples/vectorsdb/delete-collection.md create mode 100644 docs/examples/vectorsdb/delete-document.md create mode 100644 docs/examples/vectorsdb/delete-documents.md create mode 100644 docs/examples/vectorsdb/delete-index.md create mode 100644 docs/examples/vectorsdb/delete-transaction.md create mode 100644 docs/examples/vectorsdb/delete.md create mode 100644 docs/examples/vectorsdb/get-collection.md create mode 100644 docs/examples/vectorsdb/get-document.md create mode 100644 docs/examples/vectorsdb/get-index.md create mode 100644 docs/examples/vectorsdb/get-replicas.md create mode 100644 docs/examples/vectorsdb/get-status.md create mode 100644 docs/examples/vectorsdb/get-transaction.md create mode 100644 docs/examples/vectorsdb/get.md create mode 100644 docs/examples/vectorsdb/list-collections.md create mode 100644 docs/examples/vectorsdb/list-documents.md create mode 100644 docs/examples/vectorsdb/list-indexes.md create mode 100644 docs/examples/vectorsdb/list-operations.md create mode 100644 docs/examples/vectorsdb/list-specifications.md create mode 100644 docs/examples/vectorsdb/list-transactions.md create mode 100644 docs/examples/vectorsdb/list.md create mode 100644 docs/examples/vectorsdb/update-collection.md create mode 100644 docs/examples/vectorsdb/update-document.md create mode 100644 docs/examples/vectorsdb/update-documents.md create mode 100644 docs/examples/vectorsdb/update-transaction.md create mode 100644 docs/examples/vectorsdb/update.md create mode 100644 docs/examples/vectorsdb/upsert-document.md create mode 100644 docs/examples/vectorsdb/upsert-documents.md create mode 100644 test/services/test_documents_db.py create mode 100644 test/services/test_mongo.py create mode 100644 test/services/test_mysql.py create mode 100644 test/services/test_postgresql.py create mode 100644 test/services/test_vectors_db.py diff --git a/CHANGELOG.md b/CHANGELOG.md index 52fb6a98..de574a2f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,19 @@ # Change Log +## 23.1.0rc1 + +* Added: `documentsDB`, `vectorsDB`, `mysql`, `postgresql`, and `mongo` services, no longer hidden from server SDKs +* Added: `DocumentsDBIndexType` and `VectorsDBIndexType` enums +* Added: dedicated database models for branches, backups, restorations, poolers, PITR windows, extensions, and executions +* Added: `PostgresExtension`, `VectorsdbCollection`, `AttributeObject`, and `AttributeVector` models +* Added: `ExecutionResourceType` enum and `resourceType` on the `Execution` model +* Added: `OAuth2HuggingFace` model and the `huggingface` OAuth provider +* Added: `userId`, `emailHash`, and `name` parameters to `avatars.getPhoto` +* Added: `error`, `containerStatus`, and `lifecycleState` on the `Database` model +* Added: `changelogWatermark` on the `DatabaseMigration` model +* Added: `total` on the `DedicatedDatabaseBranchList` model +* Updated: `DedicatedDatabaseOperation.status` documents the new `queued` state + ## 23.0.0 * Breaking: removed `account.createJWT`; use `users.createJWT` instead. A leaked JWT could mint further JWTs, letting a credential outlive its own expiry — a session cannot duplicate itself to live forever either diff --git a/appwrite/__init__.py b/appwrite/__init__.py index 0519ecba..e69de29b 100644 --- a/appwrite/__init__.py +++ b/appwrite/__init__.py @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/appwrite/client.py b/appwrite/client.py index 67ba5631..b79625dc 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -10,19 +10,20 @@ from .exception import AppwriteException from .encoders.value_class_encoder import ValueClassEncoder + class Client: def __init__(self): - self._chunk_size = 5*1024*1024 + self._chunk_size = 5 * 1024 * 1024 self._self_signed = False self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent' : f'AppwritePythonSDK/23.0.0 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent': f'AppwritePythonSDK/23.1.0rc1 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '23.0.0', - 'X-Appwrite-Response-Format' : '1.9.6', + 'x-sdk-version': '23.1.0rc1', + 'X-Appwrite-Response-Format': '1.9.6', } self._config = {} @@ -174,7 +175,7 @@ def call(self, method, path='', headers=None, params=None, response_type='json') files=files, headers=headers, verify=(not self._self_signed), - allow_redirects=False if response_type == 'location' else True + allow_redirects=False if response_type == 'location' else True, ) response.raise_for_status() @@ -197,7 +198,9 @@ def call(self, method, path='', headers=None, params=None, response_type='json') if response != None: content_type = response.headers['Content-Type'] if content_type.startswith('application/json'): - raise AppwriteException(response.json()['message'], response.status_code, response.json().get('type'), response.text) + raise AppwriteException( + response.json()['message'], response.status_code, response.json().get('type'), response.text + ) else: raise AppwriteException(response.text, response.status_code, None, response.text) else: @@ -206,11 +209,11 @@ def call(self, method, path='', headers=None, params=None, response_type='json') def chunked_upload( self, path, - headers = None, - params = None, - param_name = '', - on_progress = None, - upload_id = '' + headers=None, + params=None, + param_name='', + on_progress=None, + upload_id='', ): input_file = params[param_name] @@ -227,21 +230,17 @@ def chunked_upload( input_file.data = input.read() params[param_name] = input_file - return self.call( - 'post', - path, - headers, - params - ) + return self.call('post', path, headers, params) offset = 0 counter = 0 - try: - result = self.call('get', path + '/' + upload_id, headers) - counter = result['chunksUploaded'] - except: - pass + if upload_id: + try: + result = self.call('get', path + '/' + upload_id, headers) + counter = result['chunksUploaded'] + except: + pass if counter > 0: offset = counter * self._chunk_size @@ -250,11 +249,13 @@ def chunked_upload( chunks = [] while offset < size: end = min(offset + self._chunk_size, size) - chunks.append({ - 'index': counter, - 'start': offset, - 'end': end, - }) + chunks.append( + { + 'index': counter, + 'start': offset, + 'end': end, + } + ) offset = end counter = counter + 1 @@ -286,7 +287,7 @@ def upload_chunk(chunk, current_upload_id): chunk_input = InputFile.from_bytes( read_chunk(chunk['start'], chunk['end']), input_file.filename, - getattr(input_file, 'mime_type', None) + getattr(input_file, 'mime_type', None), ) chunk_params = {**params, param_name: chunk_input} chunk_headers = {**headers} @@ -310,13 +311,15 @@ def upload_chunk(chunk, current_upload_id): uploaded_size = chunks[0]['end'] if on_progress is not None: - on_progress({ - "$id": result.get("$id"), - "progress": uploaded_size / size * 100, - "sizeUploaded": uploaded_size, - "chunksTotal": total_chunks, - "chunksUploaded": completed_count, - }) + on_progress( + { + "$id": result.get("$id"), + "progress": uploaded_size / size * 100, + "sizeUploaded": uploaded_size, + "chunksTotal": total_chunks, + "chunksUploaded": completed_count, + } + ) def upload_remaining_chunk(chunk): nonlocal completed_count, uploaded_size, last_result, final_result @@ -328,13 +331,15 @@ def upload_remaining_chunk(chunk): if is_upload_complete(chunk_result): final_result = chunk_result if on_progress is not None: - on_progress({ - "$id": upload_id_header, - "progress": uploaded_size / size * 100, - "sizeUploaded": uploaded_size, - "chunksTotal": total_chunks, - "chunksUploaded": completed_count, - }) + on_progress( + { + "$id": upload_id_header, + "progress": uploaded_size / size * 100, + "sizeUploaded": uploaded_size, + "chunksTotal": total_chunks, + "chunksUploaded": completed_count, + } + ) with ThreadPoolExecutor(max_workers=8) as executor: futures = [executor.submit(upload_remaining_chunk, chunk) for chunk in chunks[1:]] @@ -349,8 +354,8 @@ def flatten(self, data, prefix='', stringify=False): for key in data: value = data[key] if isinstance(data, dict) else key - finalKey = prefix + '[' + key +']' if prefix else key - finalKey = prefix + '[' + str(i) +']' if isinstance(data, list) else finalKey + finalKey = prefix + '[' + key + ']' if prefix else key + finalKey = prefix + '[' + str(i) + ']' if isinstance(data, list) else finalKey i += 1 if isinstance(value, list) or isinstance(value, dict): diff --git a/appwrite/encoders/__init__.py b/appwrite/encoders/__init__.py index 0519ecba..e69de29b 100644 --- a/appwrite/encoders/__init__.py +++ b/appwrite/encoders/__init__.py @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/appwrite/encoders/value_class_encoder.py b/appwrite/encoders/value_class_encoder.py index ab46a105..96f558d2 100644 --- a/appwrite/encoders/value_class_encoder.py +++ b/appwrite/encoders/value_class_encoder.py @@ -15,6 +15,7 @@ from ..enums.relation_mutate import RelationMutate from ..enums.databases_index_type import DatabasesIndexType from ..enums.order_by import OrderBy +from ..enums.documents_db_index_type import DocumentsDBIndexType from ..enums.embedding_model import EmbeddingModel from ..enums.runtime import Runtime from ..enums.project_key_scopes import ProjectKeyScopes @@ -47,12 +48,14 @@ from ..enums.tables_db_index_type import TablesDBIndexType from ..enums.password_hash import PasswordHash from ..enums.messaging_provider_type import MessagingProviderType +from ..enums.vectors_db_index_type import VectorsDBIndexType from ..enums.database_type import DatabaseType from ..enums.database_status import DatabaseStatus from ..enums.attribute_status import AttributeStatus from ..enums.column_status import ColumnStatus from ..enums.index_status import IndexStatus from ..enums.deployment_status import DeploymentStatus +from ..enums.execution_resource_type import ExecutionResourceType from ..enums.execution_trigger import ExecutionTrigger from ..enums.execution_status import ExecutionStatus from ..enums.o_auth2_google_prompt import OAuth2GooglePrompt @@ -63,6 +66,7 @@ from ..enums.message_status import MessageStatus from ..enums.billing_plan_group import BillingPlanGroup + class ValueClassEncoder(json.JSONEncoder): def default(self, o): if isinstance(o, AppwriteModel): @@ -113,6 +117,9 @@ def default(self, o): if isinstance(o, OrderBy): return o.value + if isinstance(o, DocumentsDBIndexType): + return o.value + if isinstance(o, EmbeddingModel): return o.value @@ -209,6 +216,9 @@ def default(self, o): if isinstance(o, MessagingProviderType): return o.value + if isinstance(o, VectorsDBIndexType): + return o.value + if isinstance(o, DatabaseType): return o.value @@ -227,6 +237,9 @@ def default(self, o): if isinstance(o, DeploymentStatus): return o.value + if isinstance(o, ExecutionResourceType): + return o.value + if isinstance(o, ExecutionTrigger): return o.value diff --git a/appwrite/enums/__init__.py b/appwrite/enums/__init__.py index 0519ecba..e69de29b 100644 --- a/appwrite/enums/__init__.py +++ b/appwrite/enums/__init__.py @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/appwrite/enums/adapter.py b/appwrite/enums/adapter.py index 821aa249..ab3dbc3c 100644 --- a/appwrite/enums/adapter.py +++ b/appwrite/enums/adapter.py @@ -1,5 +1,6 @@ from enum import Enum + class Adapter(Enum): STATIC = "static" SSR = "ssr" diff --git a/appwrite/enums/attribute_status.py b/appwrite/enums/attribute_status.py index 2f3975dd..c18194ec 100644 --- a/appwrite/enums/attribute_status.py +++ b/appwrite/enums/attribute_status.py @@ -1,5 +1,6 @@ from enum import Enum + class AttributeStatus(Enum): AVAILABLE = "available" PROCESSING = "processing" diff --git a/appwrite/enums/authentication_factor.py b/appwrite/enums/authentication_factor.py index 9e1f1add..171be024 100644 --- a/appwrite/enums/authentication_factor.py +++ b/appwrite/enums/authentication_factor.py @@ -1,5 +1,6 @@ from enum import Enum + class AuthenticationFactor(Enum): EMAIL = "email" PHONE = "phone" diff --git a/appwrite/enums/authenticator_type.py b/appwrite/enums/authenticator_type.py index ee9f94a5..64fca34d 100644 --- a/appwrite/enums/authenticator_type.py +++ b/appwrite/enums/authenticator_type.py @@ -1,4 +1,5 @@ from enum import Enum + class AuthenticatorType(Enum): TOTP = "totp" diff --git a/appwrite/enums/backup_services.py b/appwrite/enums/backup_services.py index 9c53935b..1c6897cd 100644 --- a/appwrite/enums/backup_services.py +++ b/appwrite/enums/backup_services.py @@ -1,5 +1,6 @@ from enum import Enum + class BackupServices(Enum): DATABASES = "databases" TABLESDB = "tablesdb" diff --git a/appwrite/enums/billing_plan_group.py b/appwrite/enums/billing_plan_group.py index 5a659196..356139e8 100644 --- a/appwrite/enums/billing_plan_group.py +++ b/appwrite/enums/billing_plan_group.py @@ -1,5 +1,6 @@ from enum import Enum + class BillingPlanGroup(Enum): STARTER = "starter" PRO = "pro" diff --git a/appwrite/enums/browser.py b/appwrite/enums/browser.py index 02974ecb..9af34d37 100644 --- a/appwrite/enums/browser.py +++ b/appwrite/enums/browser.py @@ -1,5 +1,6 @@ from enum import Enum + class Browser(Enum): AVANT_BROWSER = "aa" ANDROID_WEBVIEW_BETA = "an" diff --git a/appwrite/enums/browser_permission.py b/appwrite/enums/browser_permission.py index f0c37696..96a8295e 100644 --- a/appwrite/enums/browser_permission.py +++ b/appwrite/enums/browser_permission.py @@ -1,5 +1,6 @@ from enum import Enum + class BrowserPermission(Enum): GEOLOCATION = "geolocation" CAMERA = "camera" diff --git a/appwrite/enums/browser_theme.py b/appwrite/enums/browser_theme.py index 5d9ba62f..ebca94fb 100644 --- a/appwrite/enums/browser_theme.py +++ b/appwrite/enums/browser_theme.py @@ -1,5 +1,6 @@ from enum import Enum + class BrowserTheme(Enum): LIGHT = "light" DARK = "dark" diff --git a/appwrite/enums/build_runtime.py b/appwrite/enums/build_runtime.py index 8472bd82..08aacade 100644 --- a/appwrite/enums/build_runtime.py +++ b/appwrite/enums/build_runtime.py @@ -1,5 +1,6 @@ from enum import Enum + class BuildRuntime(Enum): NODE_14_5 = "node-14.5" NODE_16_0 = "node-16.0" @@ -79,6 +80,7 @@ class BuildRuntime(Enum): BUN_1_1 = "bun-1.1" BUN_1_2 = "bun-1.2" BUN_1_3 = "bun-1.3" + BUN_1_4 = "bun-1.4" GO_1_23 = "go-1.23" GO_1_24 = "go-1.24" GO_1_25 = "go-1.25" diff --git a/appwrite/enums/column_status.py b/appwrite/enums/column_status.py index 7cbba2f1..2e3be7bb 100644 --- a/appwrite/enums/column_status.py +++ b/appwrite/enums/column_status.py @@ -1,5 +1,6 @@ from enum import Enum + class ColumnStatus(Enum): AVAILABLE = "available" PROCESSING = "processing" diff --git a/appwrite/enums/compression.py b/appwrite/enums/compression.py index 6d2d21ad..e87a4684 100644 --- a/appwrite/enums/compression.py +++ b/appwrite/enums/compression.py @@ -1,5 +1,6 @@ from enum import Enum + class Compression(Enum): NONE = "none" GZIP = "gzip" diff --git a/appwrite/enums/credit_card.py b/appwrite/enums/credit_card.py index 71393b34..27e804d0 100644 --- a/appwrite/enums/credit_card.py +++ b/appwrite/enums/credit_card.py @@ -1,5 +1,6 @@ from enum import Enum + class CreditCard(Enum): AMERICAN_EXPRESS = "amex" ARGENCARD = "argencard" diff --git a/appwrite/enums/database_status.py b/appwrite/enums/database_status.py index ed43ed1a..c4264fac 100644 --- a/appwrite/enums/database_status.py +++ b/appwrite/enums/database_status.py @@ -1,5 +1,6 @@ from enum import Enum + class DatabaseStatus(Enum): PROVISIONING = "provisioning" READY = "ready" diff --git a/appwrite/enums/database_type.py b/appwrite/enums/database_type.py index 0b713567..fd4c11b6 100644 --- a/appwrite/enums/database_type.py +++ b/appwrite/enums/database_type.py @@ -1,5 +1,6 @@ from enum import Enum + class DatabaseType(Enum): LEGACY = "legacy" TABLESDB = "tablesdb" diff --git a/appwrite/enums/databases_index_type.py b/appwrite/enums/databases_index_type.py index 7f897a13..58e52c17 100644 --- a/appwrite/enums/databases_index_type.py +++ b/appwrite/enums/databases_index_type.py @@ -1,5 +1,6 @@ from enum import Enum + class DatabasesIndexType(Enum): KEY = "key" FULLTEXT = "fulltext" diff --git a/appwrite/enums/deployment_download_type.py b/appwrite/enums/deployment_download_type.py index e26e2d53..638175de 100644 --- a/appwrite/enums/deployment_download_type.py +++ b/appwrite/enums/deployment_download_type.py @@ -1,5 +1,6 @@ from enum import Enum + class DeploymentDownloadType(Enum): SOURCE = "source" OUTPUT = "output" diff --git a/appwrite/enums/deployment_status.py b/appwrite/enums/deployment_status.py index d7280387..648ee9df 100644 --- a/appwrite/enums/deployment_status.py +++ b/appwrite/enums/deployment_status.py @@ -1,5 +1,6 @@ from enum import Enum + class DeploymentStatus(Enum): WAITING = "waiting" PROCESSING = "processing" diff --git a/appwrite/enums/documents_db_index_type.py b/appwrite/enums/documents_db_index_type.py new file mode 100644 index 00000000..28ed2838 --- /dev/null +++ b/appwrite/enums/documents_db_index_type.py @@ -0,0 +1,7 @@ +from enum import Enum + + +class DocumentsDBIndexType(Enum): + KEY = "key" + FULLTEXT = "fulltext" + UNIQUE = "unique" diff --git a/appwrite/enums/embedding_model.py b/appwrite/enums/embedding_model.py index 5bbf1cf9..2e0c1403 100644 --- a/appwrite/enums/embedding_model.py +++ b/appwrite/enums/embedding_model.py @@ -1,7 +1,6 @@ from enum import Enum + class EmbeddingModel(Enum): NOMIC_EMBED_TEXT = "nomic-embed-text" - EMBEDDING_GEMMA = "embedding-gemma" ALL_MINILM = "all-minilm" - BGE_SMALL = "bge-small" diff --git a/appwrite/enums/execution_method.py b/appwrite/enums/execution_method.py index d260384b..4db8d7b5 100644 --- a/appwrite/enums/execution_method.py +++ b/appwrite/enums/execution_method.py @@ -1,5 +1,6 @@ from enum import Enum + class ExecutionMethod(Enum): GET = "GET" POST = "POST" diff --git a/appwrite/enums/execution_resource_type.py b/appwrite/enums/execution_resource_type.py new file mode 100644 index 00000000..fe6295d1 --- /dev/null +++ b/appwrite/enums/execution_resource_type.py @@ -0,0 +1,6 @@ +from enum import Enum + + +class ExecutionResourceType(Enum): + FUNCTIONS = "functions" + SITES = "sites" diff --git a/appwrite/enums/execution_status.py b/appwrite/enums/execution_status.py index 99c72bbd..9e657373 100644 --- a/appwrite/enums/execution_status.py +++ b/appwrite/enums/execution_status.py @@ -1,5 +1,6 @@ from enum import Enum + class ExecutionStatus(Enum): WAITING = "waiting" PROCESSING = "processing" diff --git a/appwrite/enums/execution_trigger.py b/appwrite/enums/execution_trigger.py index 1ba2051c..02b7c791 100644 --- a/appwrite/enums/execution_trigger.py +++ b/appwrite/enums/execution_trigger.py @@ -1,5 +1,6 @@ from enum import Enum + class ExecutionTrigger(Enum): HTTP = "http" SCHEDULE = "schedule" diff --git a/appwrite/enums/flag.py b/appwrite/enums/flag.py index 7dd0a30e..3b65c2f8 100644 --- a/appwrite/enums/flag.py +++ b/appwrite/enums/flag.py @@ -1,5 +1,6 @@ from enum import Enum + class Flag(Enum): AFGHANISTAN = "af" ANGOLA = "ao" diff --git a/appwrite/enums/framework.py b/appwrite/enums/framework.py index 217150fa..013d71c4 100644 --- a/appwrite/enums/framework.py +++ b/appwrite/enums/framework.py @@ -1,5 +1,6 @@ from enum import Enum + class Framework(Enum): ANALOG = "analog" ANGULAR = "angular" diff --git a/appwrite/enums/image_format.py b/appwrite/enums/image_format.py index 332f646f..c5e2ec80 100644 --- a/appwrite/enums/image_format.py +++ b/appwrite/enums/image_format.py @@ -1,5 +1,6 @@ from enum import Enum + class ImageFormat(Enum): JPG = "jpg" JPEG = "jpeg" diff --git a/appwrite/enums/image_gravity.py b/appwrite/enums/image_gravity.py index c73678df..57c13887 100644 --- a/appwrite/enums/image_gravity.py +++ b/appwrite/enums/image_gravity.py @@ -1,5 +1,6 @@ from enum import Enum + class ImageGravity(Enum): CENTER = "center" TOP_LEFT = "top-left" diff --git a/appwrite/enums/index_status.py b/appwrite/enums/index_status.py index 1332b4fa..1470809c 100644 --- a/appwrite/enums/index_status.py +++ b/appwrite/enums/index_status.py @@ -1,5 +1,6 @@ from enum import Enum + class IndexStatus(Enum): AVAILABLE = "available" PROCESSING = "processing" diff --git a/appwrite/enums/invalidation_type.py b/appwrite/enums/invalidation_type.py index 1a8f7707..3dac8043 100644 --- a/appwrite/enums/invalidation_type.py +++ b/appwrite/enums/invalidation_type.py @@ -1,5 +1,6 @@ from enum import Enum + class InvalidationType(Enum): TAG = "tag" PATH = "path" diff --git a/appwrite/enums/message_priority.py b/appwrite/enums/message_priority.py index 0010a356..1c53d410 100644 --- a/appwrite/enums/message_priority.py +++ b/appwrite/enums/message_priority.py @@ -1,5 +1,6 @@ from enum import Enum + class MessagePriority(Enum): NORMAL = "normal" HIGH = "high" diff --git a/appwrite/enums/message_status.py b/appwrite/enums/message_status.py index b821a61b..bfb8aa3d 100644 --- a/appwrite/enums/message_status.py +++ b/appwrite/enums/message_status.py @@ -1,5 +1,6 @@ from enum import Enum + class MessageStatus(Enum): DRAFT = "draft" PROCESSING = "processing" diff --git a/appwrite/enums/messaging_provider_type.py b/appwrite/enums/messaging_provider_type.py index e6e7c079..3cd17046 100644 --- a/appwrite/enums/messaging_provider_type.py +++ b/appwrite/enums/messaging_provider_type.py @@ -1,5 +1,6 @@ from enum import Enum + class MessagingProviderType(Enum): EMAIL = "email" SMS = "sms" diff --git a/appwrite/enums/o_auth2_google_prompt.py b/appwrite/enums/o_auth2_google_prompt.py index 6b98ee62..91d13668 100644 --- a/appwrite/enums/o_auth2_google_prompt.py +++ b/appwrite/enums/o_auth2_google_prompt.py @@ -1,5 +1,6 @@ from enum import Enum + class OAuth2GooglePrompt(Enum): NONE = "none" CONSENT = "consent" diff --git a/appwrite/enums/o_auth2_oidc_prompt.py b/appwrite/enums/o_auth2_oidc_prompt.py index 0c21c203..ffb848f5 100644 --- a/appwrite/enums/o_auth2_oidc_prompt.py +++ b/appwrite/enums/o_auth2_oidc_prompt.py @@ -1,5 +1,6 @@ from enum import Enum + class OAuth2OidcPrompt(Enum): NONE = "none" LOGIN = "login" diff --git a/appwrite/enums/o_auth_provider.py b/appwrite/enums/o_auth_provider.py index e0aa4ea5..0337a809 100644 --- a/appwrite/enums/o_auth_provider.py +++ b/appwrite/enums/o_auth_provider.py @@ -1,5 +1,6 @@ from enum import Enum + class OAuthProvider(Enum): AMAZON = "amazon" APPLE = "apple" @@ -21,6 +22,7 @@ class OAuthProvider(Enum): GITHUB = "github" GITLAB = "gitlab" GOOGLE = "google" + HUGGINGFACE = "huggingface" KEYCLOAK = "keycloak" KICK = "kick" LINKEDIN = "linkedin" diff --git a/appwrite/enums/order_by.py b/appwrite/enums/order_by.py index 26510393..70cd1dff 100644 --- a/appwrite/enums/order_by.py +++ b/appwrite/enums/order_by.py @@ -1,5 +1,6 @@ from enum import Enum + class OrderBy(Enum): ASC = "asc" DESC = "desc" diff --git a/appwrite/enums/organization_key_scopes.py b/appwrite/enums/organization_key_scopes.py index bb2515df..ffa6e6a6 100644 --- a/appwrite/enums/organization_key_scopes.py +++ b/appwrite/enums/organization_key_scopes.py @@ -1,5 +1,6 @@ from enum import Enum + class OrganizationKeyScopes(Enum): PROJECTS_READ = "projects.read" PROJECTS_WRITE = "projects.write" diff --git a/appwrite/enums/password_hash.py b/appwrite/enums/password_hash.py index 8dcf2122..db6a32ee 100644 --- a/appwrite/enums/password_hash.py +++ b/appwrite/enums/password_hash.py @@ -1,5 +1,6 @@ from enum import Enum + class PasswordHash(Enum): SHA1 = "sha1" SHA224 = "sha224" diff --git a/appwrite/enums/platform_type.py b/appwrite/enums/platform_type.py index 8a87d882..16921bd8 100644 --- a/appwrite/enums/platform_type.py +++ b/appwrite/enums/platform_type.py @@ -1,5 +1,6 @@ from enum import Enum + class PlatformType(Enum): WINDOWS = "windows" APPLE = "apple" diff --git a/appwrite/enums/project_auth_method_id.py b/appwrite/enums/project_auth_method_id.py index c022f9a0..8ebb7fb3 100644 --- a/appwrite/enums/project_auth_method_id.py +++ b/appwrite/enums/project_auth_method_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectAuthMethodId(Enum): EMAIL_PASSWORD = "email-password" MAGIC_URL = "magic-url" diff --git a/appwrite/enums/project_email_template_id.py b/appwrite/enums/project_email_template_id.py index 3803eaf1..c2b97a29 100644 --- a/appwrite/enums/project_email_template_id.py +++ b/appwrite/enums/project_email_template_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectEmailTemplateId(Enum): VERIFICATION = "verification" MAGICSESSION = "magicSession" diff --git a/appwrite/enums/project_email_template_locale.py b/appwrite/enums/project_email_template_locale.py index 79f15945..7b8fe48e 100644 --- a/appwrite/enums/project_email_template_locale.py +++ b/appwrite/enums/project_email_template_locale.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectEmailTemplateLocale(Enum): AF = "af" AR_AE = "ar-ae" diff --git a/appwrite/enums/project_key_scopes.py b/appwrite/enums/project_key_scopes.py index d96ff939..83c765e3 100644 --- a/appwrite/enums/project_key_scopes.py +++ b/appwrite/enums/project_key_scopes.py @@ -1,8 +1,10 @@ from enum import Enum + class ProjectKeyScopes(Enum): PROJECT_READ = "project.read" PROJECT_WRITE = "project.write" + USAGE_READ = "usage.read" KEYS_READ = "keys.read" KEYS_WRITE = "keys.write" PLATFORMS_READ = "platforms.read" @@ -42,6 +44,18 @@ class ProjectKeyScopes(Enum): ATTRIBUTES_WRITE = "attributes.write" DOCUMENTS_READ = "documents.read" DOCUMENTS_WRITE = "documents.write" + DOCUMENTSDB_READ = "documentsdb.read" + DOCUMENTSDB_WRITE = "documentsdb.write" + DOCUMENTSDB_COLLECTIONS_READ = "documentsdb.collections.read" + DOCUMENTSDB_COLLECTIONS_WRITE = "documentsdb.collections.write" + DOCUMENTSDB_DOCUMENTS_READ = "documentsdb.documents.read" + DOCUMENTSDB_DOCUMENTS_WRITE = "documentsdb.documents.write" + VECTORSDB_READ = "vectorsdb.read" + VECTORSDB_WRITE = "vectorsdb.write" + VECTORSDB_COLLECTIONS_READ = "vectorsdb.collections.read" + VECTORSDB_COLLECTIONS_WRITE = "vectorsdb.collections.write" + VECTORSDB_DOCUMENTS_READ = "vectorsdb.documents.read" + VECTORSDB_DOCUMENTS_WRITE = "vectorsdb.documents.write" BUCKETS_READ = "buckets.read" BUCKETS_WRITE = "buckets.write" FILES_READ = "files.read" @@ -94,7 +108,6 @@ class ProjectKeyScopes(Enum): ARCHIVES_WRITE = "archives.write" RESTORATIONS_READ = "restorations.read" RESTORATIONS_WRITE = "restorations.write" - DEDICATEDDATABASES_EXECUTE = "dedicatedDatabases.execute" DOMAINS_READ = "domains.read" DOMAINS_WRITE = "domains.write" WAFRULES_READ = "wafRules.read" @@ -106,4 +119,3 @@ class ProjectKeyScopes(Enum): OAUTH2_READ = "oauth2.read" OAUTH2_WRITE = "oauth2.write" OAUTH2_INTROSPECT = "oauth2.introspect" - USAGE_READ = "usage.read" diff --git a/appwrite/enums/project_o_auth2_google_prompt.py b/appwrite/enums/project_o_auth2_google_prompt.py index 126e3760..25c6b2fb 100644 --- a/appwrite/enums/project_o_auth2_google_prompt.py +++ b/appwrite/enums/project_o_auth2_google_prompt.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectOAuth2GooglePrompt(Enum): NONE = "none" CONSENT = "consent" diff --git a/appwrite/enums/project_o_auth2_oidc_prompt.py b/appwrite/enums/project_o_auth2_oidc_prompt.py index 43c64713..3f68ee10 100644 --- a/appwrite/enums/project_o_auth2_oidc_prompt.py +++ b/appwrite/enums/project_o_auth2_oidc_prompt.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectOAuth2OidcPrompt(Enum): NONE = "none" LOGIN = "login" diff --git a/appwrite/enums/project_o_auth_provider_id.py b/appwrite/enums/project_o_auth_provider_id.py index c61f6002..3e93dacb 100644 --- a/appwrite/enums/project_o_auth_provider_id.py +++ b/appwrite/enums/project_o_auth_provider_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectOAuthProviderId(Enum): AMAZON = "amazon" APPLE = "apple" @@ -21,6 +22,7 @@ class ProjectOAuthProviderId(Enum): GITHUB = "github" GITLAB = "gitlab" GOOGLE = "google" + HUGGINGFACE = "huggingface" KEYCLOAK = "keycloak" KICK = "kick" LINKEDIN = "linkedin" diff --git a/appwrite/enums/project_policy_id.py b/appwrite/enums/project_policy_id.py index 02b97a3e..a3f06435 100644 --- a/appwrite/enums/project_policy_id.py +++ b/appwrite/enums/project_policy_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectPolicyId(Enum): PASSWORD_DICTIONARY = "password-dictionary" PASSWORD_HISTORY = "password-history" diff --git a/appwrite/enums/project_protocol_id.py b/appwrite/enums/project_protocol_id.py index 5ccc6a68..d368cf74 100644 --- a/appwrite/enums/project_protocol_id.py +++ b/appwrite/enums/project_protocol_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectProtocolId(Enum): REST = "rest" GRAPHQL = "graphql" diff --git a/appwrite/enums/project_service_id.py b/appwrite/enums/project_service_id.py index 322e6d6c..3a07a26a 100644 --- a/appwrite/enums/project_service_id.py +++ b/appwrite/enums/project_service_id.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectServiceId(Enum): ACCOUNT = "account" AVATARS = "avatars" diff --git a/appwrite/enums/project_smtp_secure.py b/appwrite/enums/project_smtp_secure.py index 8c165ea5..119b6922 100644 --- a/appwrite/enums/project_smtp_secure.py +++ b/appwrite/enums/project_smtp_secure.py @@ -1,5 +1,6 @@ from enum import Enum + class ProjectSMTPSecure(Enum): TLS = "tls" SSL = "ssl" diff --git a/appwrite/enums/proxy_resource_type.py b/appwrite/enums/proxy_resource_type.py index 8b9378da..2ac23ae3 100644 --- a/appwrite/enums/proxy_resource_type.py +++ b/appwrite/enums/proxy_resource_type.py @@ -1,5 +1,6 @@ from enum import Enum + class ProxyResourceType(Enum): SITE = "site" FUNCTION = "function" diff --git a/appwrite/enums/proxy_rule_deployment_resource_type.py b/appwrite/enums/proxy_rule_deployment_resource_type.py index 9013ed02..8d525d0c 100644 --- a/appwrite/enums/proxy_rule_deployment_resource_type.py +++ b/appwrite/enums/proxy_rule_deployment_resource_type.py @@ -1,5 +1,6 @@ from enum import Enum + class ProxyRuleDeploymentResourceType(Enum): FUNCTION = "function" SITE = "site" diff --git a/appwrite/enums/proxy_rule_status.py b/appwrite/enums/proxy_rule_status.py index 29ab0713..28c84051 100644 --- a/appwrite/enums/proxy_rule_status.py +++ b/appwrite/enums/proxy_rule_status.py @@ -1,5 +1,6 @@ from enum import Enum + class ProxyRuleStatus(Enum): UNVERIFIED = "unverified" VERIFYING = "verifying" diff --git a/appwrite/enums/region.py b/appwrite/enums/region.py index dd8c47c5..748363c5 100644 --- a/appwrite/enums/region.py +++ b/appwrite/enums/region.py @@ -1,5 +1,6 @@ from enum import Enum + class Region(Enum): FRA = "fra" NYC = "nyc" diff --git a/appwrite/enums/relation_mutate.py b/appwrite/enums/relation_mutate.py index ae52aa7f..e280c10f 100644 --- a/appwrite/enums/relation_mutate.py +++ b/appwrite/enums/relation_mutate.py @@ -1,5 +1,6 @@ from enum import Enum + class RelationMutate(Enum): CASCADE = "cascade" RESTRICT = "restrict" diff --git a/appwrite/enums/relationship_type.py b/appwrite/enums/relationship_type.py index 7866ca6d..45a7e89c 100644 --- a/appwrite/enums/relationship_type.py +++ b/appwrite/enums/relationship_type.py @@ -1,5 +1,6 @@ from enum import Enum + class RelationshipType(Enum): ONETOONE = "oneToOne" MANYTOONE = "manyToOne" diff --git a/appwrite/enums/runtime.py b/appwrite/enums/runtime.py index 0bc261ca..e543e3bb 100644 --- a/appwrite/enums/runtime.py +++ b/appwrite/enums/runtime.py @@ -1,5 +1,6 @@ from enum import Enum + class Runtime(Enum): NODE_14_5 = "node-14.5" NODE_16_0 = "node-16.0" @@ -79,6 +80,7 @@ class Runtime(Enum): BUN_1_1 = "bun-1.1" BUN_1_2 = "bun-1.2" BUN_1_3 = "bun-1.3" + BUN_1_4 = "bun-1.4" GO_1_23 = "go-1.23" GO_1_24 = "go-1.24" GO_1_25 = "go-1.25" diff --git a/appwrite/enums/smtp_encryption.py b/appwrite/enums/smtp_encryption.py index 213330e5..d5c8a946 100644 --- a/appwrite/enums/smtp_encryption.py +++ b/appwrite/enums/smtp_encryption.py @@ -1,5 +1,6 @@ from enum import Enum + class SmtpEncryption(Enum): NONE = "none" SSL = "ssl" diff --git a/appwrite/enums/status_code.py b/appwrite/enums/status_code.py index e6f7e49e..cc44161a 100644 --- a/appwrite/enums/status_code.py +++ b/appwrite/enums/status_code.py @@ -1,5 +1,6 @@ from enum import Enum + class StatusCode(Enum): MOVEDPERMANENTLY = "301" FOUND = "302" diff --git a/appwrite/enums/tables_db_index_type.py b/appwrite/enums/tables_db_index_type.py index 5707dd7a..5c0a903c 100644 --- a/appwrite/enums/tables_db_index_type.py +++ b/appwrite/enums/tables_db_index_type.py @@ -1,5 +1,6 @@ from enum import Enum + class TablesDBIndexType(Enum): KEY = "key" FULLTEXT = "fulltext" diff --git a/appwrite/enums/template_reference_type.py b/appwrite/enums/template_reference_type.py index b523991a..723acda3 100644 --- a/appwrite/enums/template_reference_type.py +++ b/appwrite/enums/template_reference_type.py @@ -1,5 +1,6 @@ from enum import Enum + class TemplateReferenceType(Enum): COMMIT = "commit" BRANCH = "branch" diff --git a/appwrite/enums/timezone.py b/appwrite/enums/timezone.py index d68d075d..477fac21 100644 --- a/appwrite/enums/timezone.py +++ b/appwrite/enums/timezone.py @@ -1,5 +1,6 @@ from enum import Enum + class Timezone(Enum): AFRICA_ABIDJAN = "africa/abidjan" AFRICA_ACCRA = "africa/accra" diff --git a/appwrite/enums/vcs_reference_type.py b/appwrite/enums/vcs_reference_type.py index e172e638..d060a18a 100644 --- a/appwrite/enums/vcs_reference_type.py +++ b/appwrite/enums/vcs_reference_type.py @@ -1,5 +1,6 @@ from enum import Enum + class VCSReferenceType(Enum): BRANCH = "branch" COMMIT = "commit" diff --git a/appwrite/enums/vectors_db_index_type.py b/appwrite/enums/vectors_db_index_type.py new file mode 100644 index 00000000..eda503ca --- /dev/null +++ b/appwrite/enums/vectors_db_index_type.py @@ -0,0 +1,10 @@ +from enum import Enum + + +class VectorsDBIndexType(Enum): + HNSW_EUCLIDEAN = "hnsw_euclidean" + HNSW_DOT = "hnsw_dot" + HNSW_COSINE = "hnsw_cosine" + OBJECT = "object" + KEY = "key" + UNIQUE = "unique" diff --git a/appwrite/exception.py b/appwrite/exception.py index 146e7a78..04574b2a 100644 --- a/appwrite/exception.py +++ b/appwrite/exception.py @@ -1,7 +1,7 @@ class AppwriteException(Exception): - def __init__(self, message, code = 0, type = None, response = None): + def __init__(self, message, code=0, type=None, response=None): self.message = message self.code = code self.type = type self.response = response - super().__init__(self.message) \ No newline at end of file + super().__init__(self.message) diff --git a/appwrite/id.py b/appwrite/id.py index 0be30407..0fbf606f 100644 --- a/appwrite/id.py +++ b/appwrite/id.py @@ -2,6 +2,7 @@ import math import os + class ID: # Generate an hex ID based on timestamp # Recreated from https://www.php.net/manual/en/function.uniqid.php @@ -9,7 +10,7 @@ class ID: def __hex_timestamp(): now = datetime.now() sec = int(now.timestamp()) - usec = (now.microsecond % 1000) + usec = now.microsecond % 1000 hex_timestamp = f'{sec:08x}{usec:05x}' return hex_timestamp @@ -19,7 +20,7 @@ def custom(id): # Generate a unique ID with padding to have a longer ID @staticmethod - def unique(padding = 7): + def unique(padding=7): base_id = ID.__hex_timestamp() random_bytes = os.urandom(math.ceil(padding / 2)) random_padding = random_bytes.hex()[:padding] diff --git a/appwrite/input_file.py b/appwrite/input_file.py index 33d5a777..8d8f98c4 100644 --- a/appwrite/input_file.py +++ b/appwrite/input_file.py @@ -1,6 +1,7 @@ import os import mimetypes + class InputFile: @classmethod def from_path(cls, path): @@ -12,10 +13,10 @@ def from_path(cls, path): return instance @classmethod - def from_bytes(cls, bytes, filename, mime_type = None): + def from_bytes(cls, bytes, filename, mime_type=None): instance = cls() instance.data = bytes instance.filename = filename instance.mime_type = mime_type instance.source_type = 'bytes' - return instance \ No newline at end of file + return instance diff --git a/appwrite/models/__init__.py b/appwrite/models/__init__.py index 9b7d0ced..507139f4 100644 --- a/appwrite/models/__init__.py +++ b/appwrite/models/__init__.py @@ -43,6 +43,7 @@ from .target_list import TargetList from .transaction_list import TransactionList from .specification_list import SpecificationList +from .vectorsdb_collection_list import VectorsdbCollectionList from .embedding_list import EmbeddingList from .insight_list import InsightList from .report_list import ReportList @@ -68,6 +69,9 @@ from .attribute_text import AttributeText from .attribute_mediumtext import AttributeMediumtext from .attribute_longtext import AttributeLongtext +from .vectorsdb_collection import VectorsdbCollection +from .attribute_object import AttributeObject +from .attribute_vector import AttributeVector from .table import Table from .column_list import ColumnList from .column_string import ColumnString @@ -153,6 +157,7 @@ from .o_auth2_notion import OAuth2Notion from .o_auth2_salesforce import OAuth2Salesforce from .o_auth2_yahoo import OAuth2Yahoo +from .o_auth2_hugging_face import OAuth2HuggingFace from .o_auth2_linkedin import OAuth2Linkedin from .o_auth2_disqus import OAuth2Disqus from .o_auth2_amazon import OAuth2Amazon @@ -216,6 +221,9 @@ from .activity_event import ActivityEvent from .additional_resource import AdditionalResource from .backup_archive import BackupArchive +from .dedicated_database_backup import DedicatedDatabaseBackup +from .dedicated_database_backup_list import DedicatedDatabaseBackupList +from .dedicated_database_backup_storage import DedicatedDatabaseBackupStorage from .billing_limits import BillingLimits from .billing_plan import BillingPlan from .billing_plan_addon import BillingPlanAddon @@ -224,22 +232,32 @@ from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits from .billing_plan_supported_addons import BillingPlanSupportedAddons from .block import Block +from .dedicated_database_branch import DedicatedDatabaseBranch +from .dedicated_database_branch_list import DedicatedDatabaseBranchList from .database_migration import DatabaseMigration from .dedicated_database import DedicatedDatabase +from .dedicated_database_execution import DedicatedDatabaseExecution +from .dedicated_database_execution_column import DedicatedDatabaseExecutionColumn +from .dedicated_database_restoration import DedicatedDatabaseRestoration from .database_status import DatabaseStatus +from .dedicated_database_extensions import DedicatedDatabaseExtensions from .dedicated_database_member import DedicatedDatabaseMember from .dedicated_database_operation import DedicatedDatabaseOperation from .dedicated_database_operation_list import DedicatedDatabaseOperationList from .dedicated_database_replicas import DedicatedDatabaseReplicas from .proxy_invalidation import ProxyInvalidation from .organization import Organization +from .dedicated_database_pitr_windows import DedicatedDatabasePITRWindows from .backup_policy import BackupPolicy from .policy_deny_aliased_email import PolicyDenyAliasedEmail from .policy_deny_disposable_email import PolicyDenyDisposableEmail from .policy_deny_free_email import PolicyDenyFreeEmail from .policy_deny_corporate_email import PolicyDenyCorporateEmail +from .dedicated_database_pooler import DedicatedDatabasePooler +from .postgres_extension import PostgresExtension from .program import Program from .backup_restoration import BackupRestoration +from .dedicated_database_restoration_list import DedicatedDatabaseRestorationList from .dedicated_database_specification import DedicatedDatabaseSpecification from .dedicated_database_specification_list import DedicatedDatabaseSpecificationList from .dedicated_database_specification_pricing import DedicatedDatabaseSpecificationPricing @@ -273,6 +291,7 @@ from .backup_policy_list import BackupPolicyList from .backup_restoration_list import BackupRestorationList from .database_migration_list import DatabaseMigrationList +from .dedicated_database_list import DedicatedDatabaseList from .apps_list import AppsList from .app_secret_list import AppSecretList from .app_scope_list import AppScopeList @@ -325,6 +344,7 @@ 'TargetList', 'TransactionList', 'SpecificationList', + 'VectorsdbCollectionList', 'EmbeddingList', 'InsightList', 'ReportList', @@ -350,6 +370,9 @@ 'AttributeText', 'AttributeMediumtext', 'AttributeLongtext', + 'VectorsdbCollection', + 'AttributeObject', + 'AttributeVector', 'Table', 'ColumnList', 'ColumnString', @@ -435,6 +458,7 @@ 'OAuth2Notion', 'OAuth2Salesforce', 'OAuth2Yahoo', + 'OAuth2HuggingFace', 'OAuth2Linkedin', 'OAuth2Disqus', 'OAuth2Amazon', @@ -498,6 +522,9 @@ 'ActivityEvent', 'AdditionalResource', 'BackupArchive', + 'DedicatedDatabaseBackup', + 'DedicatedDatabaseBackupList', + 'DedicatedDatabaseBackupStorage', 'BillingLimits', 'BillingPlan', 'BillingPlanAddon', @@ -506,22 +533,32 @@ 'BillingPlanDedicatedDatabaseLimits', 'BillingPlanSupportedAddons', 'Block', + 'DedicatedDatabaseBranch', + 'DedicatedDatabaseBranchList', 'DatabaseMigration', 'DedicatedDatabase', + 'DedicatedDatabaseExecution', + 'DedicatedDatabaseExecutionColumn', + 'DedicatedDatabaseRestoration', 'DatabaseStatus', + 'DedicatedDatabaseExtensions', 'DedicatedDatabaseMember', 'DedicatedDatabaseOperation', 'DedicatedDatabaseOperationList', 'DedicatedDatabaseReplicas', 'ProxyInvalidation', 'Organization', + 'DedicatedDatabasePITRWindows', 'BackupPolicy', 'PolicyDenyAliasedEmail', 'PolicyDenyDisposableEmail', 'PolicyDenyFreeEmail', 'PolicyDenyCorporateEmail', + 'DedicatedDatabasePooler', + 'PostgresExtension', 'Program', 'BackupRestoration', + 'DedicatedDatabaseRestorationList', 'DedicatedDatabaseSpecification', 'DedicatedDatabaseSpecificationList', 'DedicatedDatabaseSpecificationPricing', @@ -555,6 +592,7 @@ 'BackupPolicyList', 'BackupRestorationList', 'DatabaseMigrationList', + 'DedicatedDatabaseList', 'AppsList', 'AppSecretList', 'AppScopeList', diff --git a/appwrite/models/activity_event.py b/appwrite/models/activity_event.py index eddec37d..d94a171c 100644 --- a/appwrite/models/activity_event.py +++ b/appwrite/models/activity_event.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class ActivityEvent(AppwriteModel): """ ActivityEvent @@ -68,6 +69,7 @@ class ActivityEvent(AppwriteModel): sdkversion : str Version of the SDK that triggered the event. """ + id: str = Field(..., alias='$id') actortype: str = Field(..., alias='actorType') actorid: str = Field(..., alias='actorId') diff --git a/appwrite/models/activity_event_list.py b/appwrite/models/activity_event_list.py index 8e5ad682..017b6ed0 100644 --- a/appwrite/models/activity_event_list.py +++ b/appwrite/models/activity_event_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .activity_event import ActivityEvent + class ActivityEventList(AppwriteModel): """ Activity event list @@ -15,5 +16,6 @@ class ActivityEventList(AppwriteModel): events : List[ActivityEvent] List of events. """ + total: float = Field(..., alias='total') events: List[ActivityEvent] = Field(..., alias='events') diff --git a/appwrite/models/additional_resource.py b/appwrite/models/additional_resource.py index 63e01170..4fc5c0e1 100644 --- a/appwrite/models/additional_resource.py +++ b/appwrite/models/additional_resource.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AdditionalResource(AppwriteModel): """ AdditionalResource @@ -22,6 +23,7 @@ class AdditionalResource(AppwriteModel): invoicedesc : str Description on invoice """ + name: str = Field(..., alias='name') unit: str = Field(..., alias='unit') currency: str = Field(..., alias='currency') diff --git a/appwrite/models/algo_argon2.py b/appwrite/models/algo_argon2.py index 7a36400b..f219224e 100644 --- a/appwrite/models/algo_argon2.py +++ b/appwrite/models/algo_argon2.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoArgon2(AppwriteModel): """ AlgoArgon2 @@ -18,6 +19,7 @@ class AlgoArgon2(AppwriteModel): threads : float Number of threads used to compute hash. """ + type: str = Field(..., alias='type') memorycost: float = Field(..., alias='memoryCost') timecost: float = Field(..., alias='timeCost') diff --git a/appwrite/models/algo_bcrypt.py b/appwrite/models/algo_bcrypt.py index da13f693..4fd4c9e3 100644 --- a/appwrite/models/algo_bcrypt.py +++ b/appwrite/models/algo_bcrypt.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoBcrypt(AppwriteModel): """ AlgoBcrypt @@ -12,4 +13,5 @@ class AlgoBcrypt(AppwriteModel): type : str Algo type. """ + type: str = Field(..., alias='type') diff --git a/appwrite/models/algo_md5.py b/appwrite/models/algo_md5.py index a907b243..aa7df63f 100644 --- a/appwrite/models/algo_md5.py +++ b/appwrite/models/algo_md5.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoMd5(AppwriteModel): """ AlgoMD5 @@ -12,4 +13,5 @@ class AlgoMd5(AppwriteModel): type : str Algo type. """ + type: str = Field(..., alias='type') diff --git a/appwrite/models/algo_phpass.py b/appwrite/models/algo_phpass.py index b899255c..3c55ac51 100644 --- a/appwrite/models/algo_phpass.py +++ b/appwrite/models/algo_phpass.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoPhpass(AppwriteModel): """ AlgoPHPass @@ -12,4 +13,5 @@ class AlgoPhpass(AppwriteModel): type : str Algo type. """ + type: str = Field(..., alias='type') diff --git a/appwrite/models/algo_scrypt.py b/appwrite/models/algo_scrypt.py index b88ae26e..1eb89f7c 100644 --- a/appwrite/models/algo_scrypt.py +++ b/appwrite/models/algo_scrypt.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoScrypt(AppwriteModel): """ AlgoScrypt @@ -20,6 +21,7 @@ class AlgoScrypt(AppwriteModel): length : float Length used to compute hash. """ + type: str = Field(..., alias='type') costcpu: float = Field(..., alias='costCpu') costmemory: float = Field(..., alias='costMemory') diff --git a/appwrite/models/algo_scrypt_modified.py b/appwrite/models/algo_scrypt_modified.py index a6bc6fb1..76f96b48 100644 --- a/appwrite/models/algo_scrypt_modified.py +++ b/appwrite/models/algo_scrypt_modified.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoScryptModified(AppwriteModel): """ AlgoScryptModified @@ -18,6 +19,7 @@ class AlgoScryptModified(AppwriteModel): signerkey : str Key used to compute hash. """ + type: str = Field(..., alias='type') salt: str = Field(..., alias='salt') saltseparator: str = Field(..., alias='saltSeparator') diff --git a/appwrite/models/algo_sha.py b/appwrite/models/algo_sha.py index c7809040..e091c43f 100644 --- a/appwrite/models/algo_sha.py +++ b/appwrite/models/algo_sha.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AlgoSha(AppwriteModel): """ AlgoSHA @@ -12,4 +13,5 @@ class AlgoSha(AppwriteModel): type : str Algo type. """ + type: str = Field(..., alias='type') diff --git a/appwrite/models/app.py b/appwrite/models/app.py index 76e93798..570d8681 100644 --- a/appwrite/models/app.py +++ b/appwrite/models/app.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app_secret import AppSecret + class App(AppwriteModel): """ App @@ -63,6 +64,7 @@ class App(AppwriteModel): secrets : List[AppSecret] List of application secrets. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/app_installation.py b/appwrite/models/app_installation.py index 3984389c..5dbfab42 100644 --- a/appwrite/models/app_installation.py +++ b/appwrite/models/app_installation.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AppInstallation(AppwriteModel): """ AppInstallation @@ -21,7 +22,7 @@ class AppInstallation(AppwriteModel): ID of the team the application is installed on. scopes : List[Any] Scopes granted to the application. Snapshot of the application's installation scopes taken when the installation was created or last updated. - authorizationdetails : Dict[str, Any] + authorizationdetails : List[Any] Authorization details granted to the application. Rich authorization request (RFC 9396) style entries; the Appwrite Console stores authorized project IDs here. createdbyid : str ID of the user who created the installation. @@ -30,13 +31,14 @@ class AppInstallation(AppwriteModel): lastaccessedat : Optional[str] Time an access token was last issued for the installation in ISO 8601 format. Null if never used. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') appid: str = Field(..., alias='appId') teamid: str = Field(..., alias='teamId') scopes: List[Any] = Field(..., alias='scopes') - authorizationdetails: Dict[str, Any] = Field(..., alias='authorizationDetails') + authorizationdetails: List[Any] = Field(..., alias='authorizationDetails') createdbyid: str = Field(..., alias='createdById') createdbyname: str = Field(..., alias='createdByName') lastaccessedat: Optional[str] = Field(default=None, alias='lastAccessedAt') diff --git a/appwrite/models/app_installation_list.py b/appwrite/models/app_installation_list.py index 0519077d..eb06054c 100644 --- a/appwrite/models/app_installation_list.py +++ b/appwrite/models/app_installation_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app_installation import AppInstallation + class AppInstallationList(AppwriteModel): """ App installations list @@ -15,5 +16,6 @@ class AppInstallationList(AppwriteModel): installations : List[AppInstallation] List of installations. """ + total: float = Field(..., alias='total') installations: List[AppInstallation] = Field(..., alias='installations') diff --git a/appwrite/models/app_key.py b/appwrite/models/app_key.py index 88a319f2..8221aa10 100644 --- a/appwrite/models/app_key.py +++ b/appwrite/models/app_key.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AppKey(AppwriteModel): """ AppKey @@ -28,6 +29,7 @@ class AppKey(AppwriteModel): lastaccessedat : Optional[str] Time the app key was last used for authentication in ISO 8601 format. Null if never used. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/app_key_list.py b/appwrite/models/app_key_list.py index 2d4b7ff4..32ecb90c 100644 --- a/appwrite/models/app_key_list.py +++ b/appwrite/models/app_key_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app_key import AppKey + class AppKeyList(AppwriteModel): """ App keys list @@ -15,5 +16,6 @@ class AppKeyList(AppwriteModel): keys : List[AppKey] List of keys. """ + total: float = Field(..., alias='total') keys: List[AppKey] = Field(..., alias='keys') diff --git a/appwrite/models/app_scope.py b/appwrite/models/app_scope.py index 4dca2ae2..ee295c5e 100644 --- a/appwrite/models/app_scope.py +++ b/appwrite/models/app_scope.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AppScope(AppwriteModel): """ AppScope @@ -20,6 +21,7 @@ class AppScope(AppwriteModel): deprecated : bool Whether the scope is deprecated. Deprecated scopes can still be requested but should not be offered for new grants. """ + value: str = Field(..., alias='value') description: str = Field(..., alias='description') type: str = Field(..., alias='type') diff --git a/appwrite/models/app_scope_list.py b/appwrite/models/app_scope_list.py index f92908e7..ef9484d4 100644 --- a/appwrite/models/app_scope_list.py +++ b/appwrite/models/app_scope_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app_scope import AppScope + class AppScopeList(AppwriteModel): """ App scopes list @@ -15,5 +16,6 @@ class AppScopeList(AppwriteModel): scopes : List[AppScope] List of scopes. """ + total: float = Field(..., alias='total') scopes: List[AppScope] = Field(..., alias='scopes') diff --git a/appwrite/models/app_secret.py b/appwrite/models/app_secret.py index 348b2cbf..2e2b8d49 100644 --- a/appwrite/models/app_secret.py +++ b/appwrite/models/app_secret.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AppSecret(AppwriteModel): """ AppSecret @@ -28,6 +29,7 @@ class AppSecret(AppwriteModel): lastaccessedat : Optional[str] Time the secret was last used for authentication in ISO 8601 format. Null if never used. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/app_secret_list.py b/appwrite/models/app_secret_list.py index c5e84728..6b248dba 100644 --- a/appwrite/models/app_secret_list.py +++ b/appwrite/models/app_secret_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app_secret import AppSecret + class AppSecretList(AppwriteModel): """ App secrets list @@ -15,5 +16,6 @@ class AppSecretList(AppwriteModel): secrets : List[AppSecret] List of secrets. """ + total: float = Field(..., alias='total') secrets: List[AppSecret] = Field(..., alias='secrets') diff --git a/appwrite/models/app_secret_plaintext.py b/appwrite/models/app_secret_plaintext.py index 18a32d13..6b7299b2 100644 --- a/appwrite/models/app_secret_plaintext.py +++ b/appwrite/models/app_secret_plaintext.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class AppSecretPlaintext(AppwriteModel): """ AppSecretPlaintext @@ -28,6 +29,7 @@ class AppSecretPlaintext(AppwriteModel): lastaccessedat : Optional[str] Time the secret was last used for authentication in ISO 8601 format. Null if never used. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/apps_list.py b/appwrite/models/apps_list.py index dd11e26d..965805a6 100644 --- a/appwrite/models/apps_list.py +++ b/appwrite/models/apps_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .app import App + class AppsList(AppwriteModel): """ Apps list @@ -15,5 +16,6 @@ class AppsList(AppwriteModel): apps : List[App] List of apps. """ + total: float = Field(..., alias='total') apps: List[App] = Field(..., alias='apps') diff --git a/appwrite/models/attribute_bigint.py b/appwrite/models/attribute_bigint.py index aae6fd2d..5ceedae3 100644 --- a/appwrite/models/attribute_bigint.py +++ b/appwrite/models/attribute_bigint.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeBigint(AppwriteModel): """ AttributeBigInt @@ -33,6 +34,7 @@ class AttributeBigint(AppwriteModel): default : Optional[float] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_boolean.py b/appwrite/models/attribute_boolean.py index af48afef..bca29adc 100644 --- a/appwrite/models/attribute_boolean.py +++ b/appwrite/models/attribute_boolean.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeBoolean(AppwriteModel): """ AttributeBoolean @@ -29,6 +30,7 @@ class AttributeBoolean(AppwriteModel): default : Optional[bool] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_datetime.py b/appwrite/models/attribute_datetime.py index 90295f5b..40c7d492 100644 --- a/appwrite/models/attribute_datetime.py +++ b/appwrite/models/attribute_datetime.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeDatetime(AppwriteModel): """ AttributeDatetime @@ -31,6 +32,7 @@ class AttributeDatetime(AppwriteModel): default : Optional[str] Default value for attribute when not provided. Only null is optional """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_email.py b/appwrite/models/attribute_email.py index 498c5120..15a5dcd8 100644 --- a/appwrite/models/attribute_email.py +++ b/appwrite/models/attribute_email.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeEmail(AppwriteModel): """ AttributeEmail @@ -31,6 +32,7 @@ class AttributeEmail(AppwriteModel): default : Optional[str] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_enum.py b/appwrite/models/attribute_enum.py index 0059a9a4..275abd2f 100644 --- a/appwrite/models/attribute_enum.py +++ b/appwrite/models/attribute_enum.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeEnum(AppwriteModel): """ AttributeEnum @@ -33,6 +34,7 @@ class AttributeEnum(AppwriteModel): default : Optional[str] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_float.py b/appwrite/models/attribute_float.py index 2de6c42f..5b989c16 100644 --- a/appwrite/models/attribute_float.py +++ b/appwrite/models/attribute_float.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeFloat(AppwriteModel): """ AttributeFloat @@ -33,6 +34,7 @@ class AttributeFloat(AppwriteModel): default : Optional[float] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_integer.py b/appwrite/models/attribute_integer.py index dcf8a923..586d41b5 100644 --- a/appwrite/models/attribute_integer.py +++ b/appwrite/models/attribute_integer.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeInteger(AppwriteModel): """ AttributeInteger @@ -33,6 +34,7 @@ class AttributeInteger(AppwriteModel): default : Optional[float] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_ip.py b/appwrite/models/attribute_ip.py index ed3bc2e5..13737149 100644 --- a/appwrite/models/attribute_ip.py +++ b/appwrite/models/attribute_ip.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeIp(AppwriteModel): """ AttributeIP @@ -31,6 +32,7 @@ class AttributeIp(AppwriteModel): default : Optional[str] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_line.py b/appwrite/models/attribute_line.py index 1313a623..4e0982d4 100644 --- a/appwrite/models/attribute_line.py +++ b/appwrite/models/attribute_line.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeLine(AppwriteModel): """ AttributeLine @@ -29,6 +30,7 @@ class AttributeLine(AppwriteModel): default : Optional[List[Any]] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_list.py b/appwrite/models/attribute_list.py index 0c98c95d..b631a4d6 100644 --- a/appwrite/models/attribute_list.py +++ b/appwrite/models/attribute_list.py @@ -21,6 +21,7 @@ from .attribute_longtext import AttributeLongtext from .attribute_string import AttributeString + class AttributeList(AppwriteModel): """ Attributes List @@ -32,5 +33,27 @@ class AttributeList(AppwriteModel): attributes : List[Union[AttributeBoolean, AttributeBigint, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributePoint, AttributeLine, AttributePolygon, AttributeVarchar, AttributeText, AttributeMediumtext, AttributeLongtext, AttributeString]] List of attributes. """ + total: float = Field(..., alias='total') - attributes: List[Union[AttributeBoolean, AttributeBigint, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributePoint, AttributeLine, AttributePolygon, AttributeVarchar, AttributeText, AttributeMediumtext, AttributeLongtext, AttributeString]] = Field(..., alias='attributes') + attributes: List[ + Union[ + AttributeBoolean, + AttributeBigint, + AttributeInteger, + AttributeFloat, + AttributeEmail, + AttributeEnum, + AttributeUrl, + AttributeIp, + AttributeDatetime, + AttributeRelationship, + AttributePoint, + AttributeLine, + AttributePolygon, + AttributeVarchar, + AttributeText, + AttributeMediumtext, + AttributeLongtext, + AttributeString, + ] + ] = Field(..., alias='attributes') diff --git a/appwrite/models/attribute_longtext.py b/appwrite/models/attribute_longtext.py index 48066791..cc03d9cf 100644 --- a/appwrite/models/attribute_longtext.py +++ b/appwrite/models/attribute_longtext.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeLongtext(AppwriteModel): """ AttributeLongtext @@ -31,6 +32,7 @@ class AttributeLongtext(AppwriteModel): encrypt : Optional[bool] Defines whether this attribute is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_mediumtext.py b/appwrite/models/attribute_mediumtext.py index eb309c72..40404d23 100644 --- a/appwrite/models/attribute_mediumtext.py +++ b/appwrite/models/attribute_mediumtext.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeMediumtext(AppwriteModel): """ AttributeMediumtext @@ -31,6 +32,7 @@ class AttributeMediumtext(AppwriteModel): encrypt : Optional[bool] Defines whether this attribute is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_object.py b/appwrite/models/attribute_object.py new file mode 100644 index 00000000..c79160bf --- /dev/null +++ b/appwrite/models/attribute_object.py @@ -0,0 +1,39 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from ..enums.attribute_status import AttributeStatus + + +class AttributeObject(AppwriteModel): + """ + AttributeObject + + Attributes + ---------- + key : str + Attribute Key. + type : str + Attribute type. + status : AttributeStatus + Attribute status. Possible values: `available`, `processing`, `deleting`, `stuck`, or `failed` + error : str + Error message. Displays error generated on failure of creating or deleting an attribute. + required : bool + Is attribute required? + array : Optional[bool] + Is attribute an array? + createdat : str + Attribute creation date in ISO 8601 format. + updatedat : str + Attribute update date in ISO 8601 format. + """ + + key: str = Field(..., alias='key') + type: str = Field(..., alias='type') + status: AttributeStatus = Field(..., alias='status') + error: str = Field(..., alias='error') + required: bool = Field(..., alias='required') + array: Optional[bool] = Field(default=None, alias='array') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/attribute_point.py b/appwrite/models/attribute_point.py index 9c89b109..c658fdf4 100644 --- a/appwrite/models/attribute_point.py +++ b/appwrite/models/attribute_point.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributePoint(AppwriteModel): """ AttributePoint @@ -29,6 +30,7 @@ class AttributePoint(AppwriteModel): default : Optional[List[Any]] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_polygon.py b/appwrite/models/attribute_polygon.py index 9a9411e3..79ca2978 100644 --- a/appwrite/models/attribute_polygon.py +++ b/appwrite/models/attribute_polygon.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributePolygon(AppwriteModel): """ AttributePolygon @@ -29,6 +30,7 @@ class AttributePolygon(AppwriteModel): default : Optional[List[Any]] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_relationship.py b/appwrite/models/attribute_relationship.py index d2421626..540e6e88 100644 --- a/appwrite/models/attribute_relationship.py +++ b/appwrite/models/attribute_relationship.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeRelationship(AppwriteModel): """ AttributeRelationship @@ -39,6 +40,7 @@ class AttributeRelationship(AppwriteModel): side : str Whether this is the parent or child side of the relationship """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_string.py b/appwrite/models/attribute_string.py index 22b3789d..e1d101a7 100644 --- a/appwrite/models/attribute_string.py +++ b/appwrite/models/attribute_string.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeString(AppwriteModel): """ AttributeString @@ -33,6 +34,7 @@ class AttributeString(AppwriteModel): encrypt : Optional[bool] Defines whether this attribute is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_text.py b/appwrite/models/attribute_text.py index 141f315c..e819094d 100644 --- a/appwrite/models/attribute_text.py +++ b/appwrite/models/attribute_text.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeText(AppwriteModel): """ AttributeText @@ -31,6 +32,7 @@ class AttributeText(AppwriteModel): encrypt : Optional[bool] Defines whether this attribute is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_url.py b/appwrite/models/attribute_url.py index bcc581ea..eb4fe4f6 100644 --- a/appwrite/models/attribute_url.py +++ b/appwrite/models/attribute_url.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeUrl(AppwriteModel): """ AttributeURL @@ -31,6 +32,7 @@ class AttributeUrl(AppwriteModel): default : Optional[str] Default value for attribute when not provided. Cannot be set when attribute is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_varchar.py b/appwrite/models/attribute_varchar.py index 1c472976..47fdb2fb 100644 --- a/appwrite/models/attribute_varchar.py +++ b/appwrite/models/attribute_varchar.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.attribute_status import AttributeStatus + class AttributeVarchar(AppwriteModel): """ AttributeVarchar @@ -33,6 +34,7 @@ class AttributeVarchar(AppwriteModel): encrypt : Optional[bool] Defines whether this attribute is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: AttributeStatus = Field(..., alias='status') diff --git a/appwrite/models/attribute_vector.py b/appwrite/models/attribute_vector.py new file mode 100644 index 00000000..4bcac94c --- /dev/null +++ b/appwrite/models/attribute_vector.py @@ -0,0 +1,42 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from ..enums.attribute_status import AttributeStatus + + +class AttributeVector(AppwriteModel): + """ + AttributeVector + + Attributes + ---------- + key : str + Attribute Key. + type : str + Attribute type. + status : AttributeStatus + Attribute status. Possible values: `available`, `processing`, `deleting`, `stuck`, or `failed` + error : str + Error message. Displays error generated on failure of creating or deleting an attribute. + required : bool + Is attribute required? + array : Optional[bool] + Is attribute an array? + createdat : str + Attribute creation date in ISO 8601 format. + updatedat : str + Attribute update date in ISO 8601 format. + size : float + Vector dimensions. + """ + + key: str = Field(..., alias='key') + type: str = Field(..., alias='type') + status: AttributeStatus = Field(..., alias='status') + error: str = Field(..., alias='error') + required: bool = Field(..., alias='required') + array: Optional[bool] = Field(default=None, alias='array') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + size: float = Field(..., alias='size') diff --git a/appwrite/models/backup_archive.py b/appwrite/models/backup_archive.py index d9d43356..060ea93c 100644 --- a/appwrite/models/backup_archive.py +++ b/appwrite/models/backup_archive.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BackupArchive(AppwriteModel): """ Archive @@ -34,6 +35,7 @@ class BackupArchive(AppwriteModel): resourcetype : Optional[str] The resource type to backup. Set only if this archive should backup a single resource. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/backup_archive_list.py b/appwrite/models/backup_archive_list.py index d91188be..da2f9f2b 100644 --- a/appwrite/models/backup_archive_list.py +++ b/appwrite/models/backup_archive_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .backup_archive import BackupArchive + class BackupArchiveList(AppwriteModel): """ Backup archive list @@ -15,5 +16,6 @@ class BackupArchiveList(AppwriteModel): archives : List[BackupArchive] List of archives. """ + total: float = Field(..., alias='total') archives: List[BackupArchive] = Field(..., alias='archives') diff --git a/appwrite/models/backup_policy.py b/appwrite/models/backup_policy.py index be27b567..b98ecf27 100644 --- a/appwrite/models/backup_policy.py +++ b/appwrite/models/backup_policy.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BackupPolicy(AppwriteModel): """ backup @@ -34,6 +35,7 @@ class BackupPolicy(AppwriteModel): enabled : bool Is this policy enabled. """ + id: str = Field(..., alias='$id') name: str = Field(..., alias='name') createdat: str = Field(..., alias='$createdAt') diff --git a/appwrite/models/backup_policy_list.py b/appwrite/models/backup_policy_list.py index b3e2f2d7..3e6901a6 100644 --- a/appwrite/models/backup_policy_list.py +++ b/appwrite/models/backup_policy_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .backup_policy import BackupPolicy + class BackupPolicyList(AppwriteModel): """ Backup policy list @@ -15,5 +16,6 @@ class BackupPolicyList(AppwriteModel): policies : List[BackupPolicy] List of policies. """ + total: float = Field(..., alias='total') policies: List[BackupPolicy] = Field(..., alias='policies') diff --git a/appwrite/models/backup_restoration.py b/appwrite/models/backup_restoration.py index 4e13b1e4..c00fe712 100644 --- a/appwrite/models/backup_restoration.py +++ b/appwrite/models/backup_restoration.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BackupRestoration(AppwriteModel): """ Restoration @@ -30,8 +31,9 @@ class BackupRestoration(AppwriteModel): resources : List[Any] The resources that are backed up by this policy. options : str - Optional data in key-value object. + Optional data in key-value object. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/backup_restoration_list.py b/appwrite/models/backup_restoration_list.py index d272fba8..53e57497 100644 --- a/appwrite/models/backup_restoration_list.py +++ b/appwrite/models/backup_restoration_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .backup_restoration import BackupRestoration + class BackupRestorationList(AppwriteModel): """ Backup restoration list @@ -15,5 +16,6 @@ class BackupRestorationList(AppwriteModel): restorations : List[BackupRestoration] List of restorations. """ + total: float = Field(..., alias='total') restorations: List[BackupRestoration] = Field(..., alias='restorations') diff --git a/appwrite/models/base_model.py b/appwrite/models/base_model.py index cb8a10d0..f942e958 100644 --- a/appwrite/models/base_model.py +++ b/appwrite/models/base_model.py @@ -6,6 +6,7 @@ ModelType = TypeVar('ModelType', bound='AppwriteModel') + class AppwriteModel(BaseModel): model_config = ConfigDict( arbitrary_types_allowed=True, diff --git a/appwrite/models/billing_limits.py b/appwrite/models/billing_limits.py index 4f9ee620..68bdc99b 100644 --- a/appwrite/models/billing_limits.py +++ b/appwrite/models/billing_limits.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BillingLimits(AppwriteModel): """ Limits @@ -26,6 +27,7 @@ class BillingLimits(AppwriteModel): budgetlimit : Optional[float] Budget limit percentage """ + bandwidth: Optional[float] = Field(default=None, alias='bandwidth') storage: Optional[float] = Field(default=None, alias='storage') users: Optional[float] = Field(default=None, alias='users') diff --git a/appwrite/models/billing_plan.py b/appwrite/models/billing_plan.py index dfe4d167..d50ea2cf 100644 --- a/appwrite/models/billing_plan.py +++ b/appwrite/models/billing_plan.py @@ -10,6 +10,7 @@ from .program import Program from .billing_plan_dedicated_database_limits import BillingPlanDedicatedDatabaseLimits + class BillingPlan(AppwriteModel): """ billingPlan @@ -122,6 +123,8 @@ class BillingPlan(AppwriteModel): Does plan support organization roles supportscredits : bool Does plan support credit + supportsdedicateddatabases : bool + Does plan support dedicated databases. supportsdisposableemailvalidation : bool Does plan support blocking disposable email addresses. supportscanonicalemailvalidation : bool @@ -152,9 +155,12 @@ class BillingPlan(AppwriteModel): Group of this billing plan for variants program : Optional[Program] Details of the program this plan is a part of. + databasecomputecredit : float + Included monthly dedicated-database compute credit in USD. Resets each billing cycle with no roll-over. dedicateddatabases : Optional[BillingPlanDedicatedDatabaseLimits] Dedicated database limits available to this plan. """ + id: str = Field(..., alias='$id') name: str = Field(..., alias='name') desc: str = Field(..., alias='desc') @@ -208,6 +214,7 @@ class BillingPlan(AppwriteModel): supportsmocknumbers: bool = Field(..., alias='supportsMockNumbers') supportsorganizationroles: bool = Field(..., alias='supportsOrganizationRoles') supportscredits: bool = Field(..., alias='supportsCredits') + supportsdedicateddatabases: bool = Field(..., alias='supportsDedicatedDatabases') supportsdisposableemailvalidation: bool = Field(..., alias='supportsDisposableEmailValidation') supportscanonicalemailvalidation: bool = Field(..., alias='supportsCanonicalEmailValidation') supportsfreeemailvalidation: bool = Field(..., alias='supportsFreeEmailValidation') @@ -223,4 +230,5 @@ class BillingPlan(AppwriteModel): limits: Optional[BillingPlanLimits] = Field(default=None, alias='limits') group: BillingPlanGroup = Field(..., alias='group') program: Optional[Program] = Field(default=None, alias='program') + databasecomputecredit: float = Field(..., alias='databaseComputeCredit') dedicateddatabases: Optional[BillingPlanDedicatedDatabaseLimits] = Field(default=None, alias='dedicatedDatabases') diff --git a/appwrite/models/billing_plan_addon.py b/appwrite/models/billing_plan_addon.py index 6ad96a36..b66dd583 100644 --- a/appwrite/models/billing_plan_addon.py +++ b/appwrite/models/billing_plan_addon.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .billing_plan_addon_details import BillingPlanAddonDetails + class BillingPlanAddon(AppwriteModel): """ Addon @@ -15,5 +16,6 @@ class BillingPlanAddon(AppwriteModel): projects : Optional[BillingPlanAddonDetails] Addon projects """ + seats: Optional[BillingPlanAddonDetails] = Field(default=None, alias='seats') projects: Optional[BillingPlanAddonDetails] = Field(default=None, alias='projects') diff --git a/appwrite/models/billing_plan_addon_details.py b/appwrite/models/billing_plan_addon_details.py index 67b2754a..8d7591f1 100644 --- a/appwrite/models/billing_plan_addon_details.py +++ b/appwrite/models/billing_plan_addon_details.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BillingPlanAddonDetails(AppwriteModel): """ Details @@ -26,6 +27,7 @@ class BillingPlanAddonDetails(AppwriteModel): invoicedesc : str Description on invoice """ + supported: bool = Field(..., alias='supported') planincluded: float = Field(..., alias='planIncluded') limit: float = Field(..., alias='limit') diff --git a/appwrite/models/billing_plan_dedicated_database_limits.py b/appwrite/models/billing_plan_dedicated_database_limits.py index 754c1666..11f4c136 100644 --- a/appwrite/models/billing_plan_dedicated_database_limits.py +++ b/appwrite/models/billing_plan_dedicated_database_limits.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BillingPlanDedicatedDatabaseLimits(AppwriteModel): """ dedicatedDatabaseLimits @@ -48,6 +49,7 @@ class BillingPlanDedicatedDatabaseLimits(AppwriteModel): allowedsyncmodes : Optional[List[Any]] Replica synchronization modes available for dedicated databases. """ + mincpu: Optional[float] = Field(default=None, alias='minCpu') maxcpu: Optional[float] = Field(default=None, alias='maxCpu') minmemorymb: Optional[float] = Field(default=None, alias='minMemoryMb') diff --git a/appwrite/models/billing_plan_limits.py b/appwrite/models/billing_plan_limits.py index 4a5abbd9..62cbdf16 100644 --- a/appwrite/models/billing_plan_limits.py +++ b/appwrite/models/billing_plan_limits.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BillingPlanLimits(AppwriteModel): """ PlanLimits @@ -14,5 +15,6 @@ class BillingPlanLimits(AppwriteModel): dailycredits : Optional[float] Daily credits limit (if applicable) """ + credits: Optional[float] = Field(default=None, alias='credits') dailycredits: Optional[float] = Field(default=None, alias='dailyCredits') diff --git a/appwrite/models/billing_plan_supported_addons.py b/appwrite/models/billing_plan_supported_addons.py index be64dde3..756a37e1 100644 --- a/appwrite/models/billing_plan_supported_addons.py +++ b/appwrite/models/billing_plan_supported_addons.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class BillingPlanSupportedAddons(AppwriteModel): """ BillingPlanSupportedAddons @@ -16,6 +17,7 @@ class BillingPlanSupportedAddons(AppwriteModel): premiumgeodborg : bool Whether the plan supports Premium Geo DB addon (organization-level) """ + baa: bool = Field(..., alias='baa') premiumgeodb: bool = Field(..., alias='premiumGeoDB') premiumgeodborg: bool = Field(..., alias='premiumGeoDBOrg') diff --git a/appwrite/models/block.py b/appwrite/models/block.py index 95ba2075..fdc801cc 100644 --- a/appwrite/models/block.py +++ b/appwrite/models/block.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Block(AppwriteModel): """ Block @@ -32,6 +33,7 @@ class Block(AppwriteModel): billingplan : str Billing plan of the organization that owns the project. """ + createdat: str = Field(..., alias='$createdAt') resourcetype: str = Field(..., alias='resourceType') resourceid: str = Field(..., alias='resourceId') diff --git a/appwrite/models/bucket.py b/appwrite/models/bucket.py index 141fe2b2..7aafabf8 100644 --- a/appwrite/models/bucket.py +++ b/appwrite/models/bucket.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Bucket(AppwriteModel): """ Bucket @@ -38,6 +39,7 @@ class Bucket(AppwriteModel): totalsize : float Total size of this bucket in bytes. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/bucket_list.py b/appwrite/models/bucket_list.py index f1dbbb07..3191bd45 100644 --- a/appwrite/models/bucket_list.py +++ b/appwrite/models/bucket_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .bucket import Bucket + class BucketList(AppwriteModel): """ Buckets List @@ -15,5 +16,6 @@ class BucketList(AppwriteModel): buckets : List[Bucket] List of buckets. """ + total: float = Field(..., alias='total') buckets: List[Bucket] = Field(..., alias='buckets') diff --git a/appwrite/models/collection.py b/appwrite/models/collection.py index d55dbe82..ab344ebc 100644 --- a/appwrite/models/collection.py +++ b/appwrite/models/collection.py @@ -22,6 +22,7 @@ from .attribute_string import AttributeString from .index import Index + class Collection(AppwriteModel): """ Collection @@ -53,6 +54,7 @@ class Collection(AppwriteModel): bytesused : float Currently used document size in bytes based on defined attributes. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -61,7 +63,28 @@ class Collection(AppwriteModel): name: str = Field(..., alias='name') enabled: bool = Field(..., alias='enabled') documentsecurity: bool = Field(..., alias='documentSecurity') - attributes: List[Union[AttributeBoolean, AttributeBigint, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributePoint, AttributeLine, AttributePolygon, AttributeVarchar, AttributeText, AttributeMediumtext, AttributeLongtext, AttributeString]] = Field(..., alias='attributes') + attributes: List[ + Union[ + AttributeBoolean, + AttributeBigint, + AttributeInteger, + AttributeFloat, + AttributeEmail, + AttributeEnum, + AttributeUrl, + AttributeIp, + AttributeDatetime, + AttributeRelationship, + AttributePoint, + AttributeLine, + AttributePolygon, + AttributeVarchar, + AttributeText, + AttributeMediumtext, + AttributeLongtext, + AttributeString, + ] + ] = Field(..., alias='attributes') indexes: List[Index] = Field(..., alias='indexes') bytesmax: float = Field(..., alias='bytesMax') bytesused: float = Field(..., alias='bytesUsed') diff --git a/appwrite/models/collection_list.py b/appwrite/models/collection_list.py index 14c896a8..87db81ed 100644 --- a/appwrite/models/collection_list.py +++ b/appwrite/models/collection_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .collection import Collection + class CollectionList(AppwriteModel): """ Collections List @@ -15,5 +16,6 @@ class CollectionList(AppwriteModel): collections : List[Collection] List of collections. """ + total: float = Field(..., alias='total') collections: List[Collection] = Field(..., alias='collections') diff --git a/appwrite/models/column_bigint.py b/appwrite/models/column_bigint.py index 2839a842..e69b46f3 100644 --- a/appwrite/models/column_bigint.py +++ b/appwrite/models/column_bigint.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnBigint(AppwriteModel): """ ColumnBigInt @@ -33,6 +34,7 @@ class ColumnBigint(AppwriteModel): default : Optional[float] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_boolean.py b/appwrite/models/column_boolean.py index f81e8ec7..0c760ff3 100644 --- a/appwrite/models/column_boolean.py +++ b/appwrite/models/column_boolean.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnBoolean(AppwriteModel): """ ColumnBoolean @@ -29,6 +30,7 @@ class ColumnBoolean(AppwriteModel): default : Optional[bool] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_datetime.py b/appwrite/models/column_datetime.py index 8345d5ef..eb06acff 100644 --- a/appwrite/models/column_datetime.py +++ b/appwrite/models/column_datetime.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnDatetime(AppwriteModel): """ ColumnDatetime @@ -31,6 +32,7 @@ class ColumnDatetime(AppwriteModel): default : Optional[str] Default value for column when not provided. Only null is optional """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_email.py b/appwrite/models/column_email.py index 7e08c1c6..2cb80040 100644 --- a/appwrite/models/column_email.py +++ b/appwrite/models/column_email.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnEmail(AppwriteModel): """ ColumnEmail @@ -31,6 +32,7 @@ class ColumnEmail(AppwriteModel): default : Optional[str] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_enum.py b/appwrite/models/column_enum.py index 8930aa95..cd3a3348 100644 --- a/appwrite/models/column_enum.py +++ b/appwrite/models/column_enum.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnEnum(AppwriteModel): """ ColumnEnum @@ -33,6 +34,7 @@ class ColumnEnum(AppwriteModel): default : Optional[str] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_float.py b/appwrite/models/column_float.py index 46c77bcb..c229043c 100644 --- a/appwrite/models/column_float.py +++ b/appwrite/models/column_float.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnFloat(AppwriteModel): """ ColumnFloat @@ -33,6 +34,7 @@ class ColumnFloat(AppwriteModel): default : Optional[float] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_index.py b/appwrite/models/column_index.py index eaa4b8d2..91ba84b7 100644 --- a/appwrite/models/column_index.py +++ b/appwrite/models/column_index.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class ColumnIndex(AppwriteModel): """ Index @@ -30,6 +31,7 @@ class ColumnIndex(AppwriteModel): orders : Optional[List[Any]] Index orders. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/column_index_list.py b/appwrite/models/column_index_list.py index fcb36452..3e3cdfdb 100644 --- a/appwrite/models/column_index_list.py +++ b/appwrite/models/column_index_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .column_index import ColumnIndex + class ColumnIndexList(AppwriteModel): """ Column Indexes List @@ -15,5 +16,6 @@ class ColumnIndexList(AppwriteModel): indexes : List[ColumnIndex] List of indexes. """ + total: float = Field(..., alias='total') indexes: List[ColumnIndex] = Field(..., alias='indexes') diff --git a/appwrite/models/column_integer.py b/appwrite/models/column_integer.py index 340dd217..f5282bc7 100644 --- a/appwrite/models/column_integer.py +++ b/appwrite/models/column_integer.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnInteger(AppwriteModel): """ ColumnInteger @@ -33,6 +34,7 @@ class ColumnInteger(AppwriteModel): default : Optional[float] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_ip.py b/appwrite/models/column_ip.py index 3240a6f6..d9c006ae 100644 --- a/appwrite/models/column_ip.py +++ b/appwrite/models/column_ip.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnIp(AppwriteModel): """ ColumnIP @@ -31,6 +32,7 @@ class ColumnIp(AppwriteModel): default : Optional[str] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_line.py b/appwrite/models/column_line.py index 280b987f..a7451f5d 100644 --- a/appwrite/models/column_line.py +++ b/appwrite/models/column_line.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnLine(AppwriteModel): """ ColumnLine @@ -29,6 +30,7 @@ class ColumnLine(AppwriteModel): default : Optional[List[Any]] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_list.py b/appwrite/models/column_list.py index 7a9635e4..bc464e88 100644 --- a/appwrite/models/column_list.py +++ b/appwrite/models/column_list.py @@ -21,6 +21,7 @@ from .column_longtext import ColumnLongtext from .column_string import ColumnString + class ColumnList(AppwriteModel): """ Columns List @@ -32,5 +33,27 @@ class ColumnList(AppwriteModel): columns : List[Union[ColumnBoolean, ColumnBigint, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnPoint, ColumnLine, ColumnPolygon, ColumnVarchar, ColumnText, ColumnMediumtext, ColumnLongtext, ColumnString]] List of columns. """ + total: float = Field(..., alias='total') - columns: List[Union[ColumnBoolean, ColumnBigint, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnPoint, ColumnLine, ColumnPolygon, ColumnVarchar, ColumnText, ColumnMediumtext, ColumnLongtext, ColumnString]] = Field(..., alias='columns') + columns: List[ + Union[ + ColumnBoolean, + ColumnBigint, + ColumnInteger, + ColumnFloat, + ColumnEmail, + ColumnEnum, + ColumnUrl, + ColumnIp, + ColumnDatetime, + ColumnRelationship, + ColumnPoint, + ColumnLine, + ColumnPolygon, + ColumnVarchar, + ColumnText, + ColumnMediumtext, + ColumnLongtext, + ColumnString, + ] + ] = Field(..., alias='columns') diff --git a/appwrite/models/column_longtext.py b/appwrite/models/column_longtext.py index 8feaa268..6df8a506 100644 --- a/appwrite/models/column_longtext.py +++ b/appwrite/models/column_longtext.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnLongtext(AppwriteModel): """ ColumnLongtext @@ -31,6 +32,7 @@ class ColumnLongtext(AppwriteModel): encrypt : Optional[bool] Defines whether this column is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_mediumtext.py b/appwrite/models/column_mediumtext.py index 817063e5..6c6f0235 100644 --- a/appwrite/models/column_mediumtext.py +++ b/appwrite/models/column_mediumtext.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnMediumtext(AppwriteModel): """ ColumnMediumtext @@ -31,6 +32,7 @@ class ColumnMediumtext(AppwriteModel): encrypt : Optional[bool] Defines whether this column is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_point.py b/appwrite/models/column_point.py index 63802f5f..3ca81d01 100644 --- a/appwrite/models/column_point.py +++ b/appwrite/models/column_point.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnPoint(AppwriteModel): """ ColumnPoint @@ -29,6 +30,7 @@ class ColumnPoint(AppwriteModel): default : Optional[List[Any]] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_polygon.py b/appwrite/models/column_polygon.py index 0cdb9903..172d7628 100644 --- a/appwrite/models/column_polygon.py +++ b/appwrite/models/column_polygon.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnPolygon(AppwriteModel): """ ColumnPolygon @@ -29,6 +30,7 @@ class ColumnPolygon(AppwriteModel): default : Optional[List[Any]] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_relationship.py b/appwrite/models/column_relationship.py index acc95a1f..32a6da3a 100644 --- a/appwrite/models/column_relationship.py +++ b/appwrite/models/column_relationship.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnRelationship(AppwriteModel): """ ColumnRelationship @@ -39,6 +40,7 @@ class ColumnRelationship(AppwriteModel): side : str Whether this is the parent or child side of the relationship """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_string.py b/appwrite/models/column_string.py index 28f5d64c..664904d2 100644 --- a/appwrite/models/column_string.py +++ b/appwrite/models/column_string.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnString(AppwriteModel): """ ColumnString @@ -33,6 +34,7 @@ class ColumnString(AppwriteModel): encrypt : Optional[bool] Defines whether this column is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_text.py b/appwrite/models/column_text.py index b0622d3c..a171fe08 100644 --- a/appwrite/models/column_text.py +++ b/appwrite/models/column_text.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnText(AppwriteModel): """ ColumnText @@ -31,6 +32,7 @@ class ColumnText(AppwriteModel): encrypt : Optional[bool] Defines whether this column is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_url.py b/appwrite/models/column_url.py index fe136927..fb1269c0 100644 --- a/appwrite/models/column_url.py +++ b/appwrite/models/column_url.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnUrl(AppwriteModel): """ ColumnURL @@ -31,6 +32,7 @@ class ColumnUrl(AppwriteModel): default : Optional[str] Default value for column when not provided. Cannot be set when column is required. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/column_varchar.py b/appwrite/models/column_varchar.py index 1c7a688e..c6ec96c5 100644 --- a/appwrite/models/column_varchar.py +++ b/appwrite/models/column_varchar.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.column_status import ColumnStatus + class ColumnVarchar(AppwriteModel): """ ColumnVarchar @@ -33,6 +34,7 @@ class ColumnVarchar(AppwriteModel): encrypt : Optional[bool] Defines whether this column is encrypted or not. """ + key: str = Field(..., alias='key') type: str = Field(..., alias='type') status: ColumnStatus = Field(..., alias='status') diff --git a/appwrite/models/continent.py b/appwrite/models/continent.py index 18f68d72..ebc9026c 100644 --- a/appwrite/models/continent.py +++ b/appwrite/models/continent.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Continent(AppwriteModel): """ Continent @@ -14,5 +15,6 @@ class Continent(AppwriteModel): code : str Continent two letter code. """ + name: str = Field(..., alias='name') code: str = Field(..., alias='code') diff --git a/appwrite/models/continent_list.py b/appwrite/models/continent_list.py index 35d970d6..a6f30050 100644 --- a/appwrite/models/continent_list.py +++ b/appwrite/models/continent_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .continent import Continent + class ContinentList(AppwriteModel): """ Continents List @@ -15,5 +16,6 @@ class ContinentList(AppwriteModel): continents : List[Continent] List of continents. """ + total: float = Field(..., alias='total') continents: List[Continent] = Field(..., alias='continents') diff --git a/appwrite/models/country.py b/appwrite/models/country.py index 46223ea6..5c40de11 100644 --- a/appwrite/models/country.py +++ b/appwrite/models/country.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Country(AppwriteModel): """ Country @@ -14,5 +15,6 @@ class Country(AppwriteModel): code : str Country two-character ISO 3166-1 alpha code. """ + name: str = Field(..., alias='name') code: str = Field(..., alias='code') diff --git a/appwrite/models/country_list.py b/appwrite/models/country_list.py index b666a97e..73dda289 100644 --- a/appwrite/models/country_list.py +++ b/appwrite/models/country_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .country import Country + class CountryList(AppwriteModel): """ Countries List @@ -15,5 +16,6 @@ class CountryList(AppwriteModel): countries : List[Country] List of countries. """ + total: float = Field(..., alias='total') countries: List[Country] = Field(..., alias='countries') diff --git a/appwrite/models/currency.py b/appwrite/models/currency.py index 4a46b04c..52eacdda 100644 --- a/appwrite/models/currency.py +++ b/appwrite/models/currency.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Currency(AppwriteModel): """ Currency @@ -24,6 +25,7 @@ class Currency(AppwriteModel): nameplural : str Currency plural name """ + symbol: str = Field(..., alias='symbol') name: str = Field(..., alias='name') symbolnative: str = Field(..., alias='symbolNative') diff --git a/appwrite/models/currency_list.py b/appwrite/models/currency_list.py index c92a05d3..c4022da6 100644 --- a/appwrite/models/currency_list.py +++ b/appwrite/models/currency_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .currency import Currency + class CurrencyList(AppwriteModel): """ Currencies List @@ -15,5 +16,6 @@ class CurrencyList(AppwriteModel): currencies : List[Currency] List of currencies. """ + total: float = Field(..., alias='total') currencies: List[Currency] = Field(..., alias='currencies') diff --git a/appwrite/models/database.py b/appwrite/models/database.py index 6c02040a..031d2e6c 100644 --- a/appwrite/models/database.py +++ b/appwrite/models/database.py @@ -7,6 +7,7 @@ from .backup_policy import BackupPolicy from .backup_archive import BackupArchive + class Database(AppwriteModel): """ Database @@ -33,11 +34,18 @@ class Database(AppwriteModel): Compute specification identifier of the dedicated backing, e.g. s-2vcpu-2gb. Null when the database has no dedicated backing. replicas : Optional[float] Number of secondary high availability replicas, excluding the primary. Null when backing configuration is unavailable. + error : Optional[str] + Error message when the dedicated backing failed. Null when the database has no dedicated backing or has not failed. + containerstatus : Optional[str] + Container status of the dedicated backing: active or inactive. Null when the database has no dedicated backing or the runtime has not reported one. + lifecyclestate : Optional[str] + Idle-lifecycle state of the dedicated backing: active, warm, cold, or hibernated. Null when the database has no dedicated backing or the runtime has not reported one. policies : Optional[List[BackupPolicy]] Database backup policies. archives : Optional[List[BackupArchive]] Database backup archives. """ + id: str = Field(..., alias='$id') name: str = Field(..., alias='name') createdat: str = Field(..., alias='$createdAt') @@ -48,5 +56,8 @@ class Database(AppwriteModel): engine: Optional[str] = Field(default=None, alias='engine') specification: Optional[str] = Field(default=None, alias='specification') replicas: Optional[float] = Field(default=None, alias='replicas') + error: Optional[str] = Field(default=None, alias='error') + containerstatus: Optional[str] = Field(default=None, alias='containerStatus') + lifecyclestate: Optional[str] = Field(default=None, alias='lifecycleState') policies: Optional[List[BackupPolicy]] = Field(default=None, alias='policies') archives: Optional[List[BackupArchive]] = Field(default=None, alias='archives') diff --git a/appwrite/models/database_list.py b/appwrite/models/database_list.py index aaa10301..a7d726c2 100644 --- a/appwrite/models/database_list.py +++ b/appwrite/models/database_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .database import Database + class DatabaseList(AppwriteModel): """ Databases List @@ -15,5 +16,6 @@ class DatabaseList(AppwriteModel): databases : List[Database] List of databases. """ + total: float = Field(..., alias='total') databases: List[Database] = Field(..., alias='databases') diff --git a/appwrite/models/database_migration.py b/appwrite/models/database_migration.py index f1bcea3b..a0acc2f2 100644 --- a/appwrite/models/database_migration.py +++ b/appwrite/models/database_migration.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DatabaseMigration(AppwriteModel): """ Database Migration @@ -29,6 +30,8 @@ class DatabaseMigration(AppwriteModel): Reason the most recent migration step failed, empty while none has. lagdocuments : float Number of documents still pending replication to the target. + changelogwatermark : float + Highest source changelog sequence applied to the target so far. verifiedat : str Time the migrated data was verified against the source in ISO 8601 format. cutoverat : str @@ -42,6 +45,7 @@ class DatabaseMigration(AppwriteModel): paused : bool Whether the migration is paused. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -52,6 +56,7 @@ class DatabaseMigration(AppwriteModel): attempt: float = Field(..., alias='attempt') lasterror: str = Field(..., alias='lastError') lagdocuments: float = Field(..., alias='lagDocuments') + changelogwatermark: float = Field(..., alias='changelogWatermark') verifiedat: str = Field(..., alias='verifiedAt') cutoverat: str = Field(..., alias='cutoverAt') soakuntil: str = Field(..., alias='soakUntil') diff --git a/appwrite/models/database_migration_list.py b/appwrite/models/database_migration_list.py index 63571efb..a8b956c4 100644 --- a/appwrite/models/database_migration_list.py +++ b/appwrite/models/database_migration_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .database_migration import DatabaseMigration + class DatabaseMigrationList(AppwriteModel): """ Database Migrations List @@ -15,5 +16,6 @@ class DatabaseMigrationList(AppwriteModel): migrations : List[DatabaseMigration] List of migrations. """ + total: float = Field(..., alias='total') migrations: List[DatabaseMigration] = Field(..., alias='migrations') diff --git a/appwrite/models/database_status.py b/appwrite/models/database_status.py index 34d3c1f6..06a7cfd4 100644 --- a/appwrite/models/database_status.py +++ b/appwrite/models/database_status.py @@ -6,6 +6,7 @@ from .database_status_replica import DatabaseStatusReplica from .database_status_volume import DatabaseStatusVolume + class DatabaseStatus(AppwriteModel): """ Status @@ -41,6 +42,7 @@ class DatabaseStatus(AppwriteModel): volumes : List[DatabaseStatusVolume] Storage volume information. """ + health: str = Field(..., alias='health') ready: bool = Field(..., alias='ready') engine: str = Field(..., alias='engine') diff --git a/appwrite/models/database_status_connections.py b/appwrite/models/database_status_connections.py index 6cfa52e2..1cce2821 100644 --- a/appwrite/models/database_status_connections.py +++ b/appwrite/models/database_status_connections.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DatabaseStatusConnections(AppwriteModel): """ Connections @@ -14,5 +15,6 @@ class DatabaseStatusConnections(AppwriteModel): max : float The engine's own max_connections. On a pooled database this is the backend limit the pooler multiplexes onto, not the ceiling a client pool may reach — that is networkMaxConnections on the database resource. """ + current: float = Field(..., alias='current') max: float = Field(..., alias='max') diff --git a/appwrite/models/database_status_replica.py b/appwrite/models/database_status_replica.py index 91428e91..cab729db 100644 --- a/appwrite/models/database_status_replica.py +++ b/appwrite/models/database_status_replica.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DatabaseStatusReplica(AppwriteModel): """ Replica @@ -15,10 +16,14 @@ class DatabaseStatusReplica(AppwriteModel): Member role. Possible values: primary (accepts reads and writes), replica (read-only follower), unknown (placement not established; reported while a transition is moving or restarting the topology, so no member can be named the write target). healthy : bool Whether the replica is healthy. + replicating : Optional[bool] + Whether the engine reports this member's replication stream as up. Null when no reading was taken: a primary has no stream to report, and a member that is not healthy, or whose probe did not answer, has none yet. `healthy` is a reachability probe of the member itself and says nothing about replication, so a healthy member may still not be replicating. lagseconds : Optional[float] - Replication lag in seconds (null for primary). + Replication lag in seconds (null for primary). Also null against `replicating: true`, for a member that is streaming but whose engine printed no numeric lag. """ + index: float = Field(..., alias='index') role: str = Field(..., alias='role') healthy: bool = Field(..., alias='healthy') + replicating: Optional[bool] = Field(default=None, alias='replicating') lagseconds: Optional[float] = Field(default=None, alias='lagSeconds') diff --git a/appwrite/models/database_status_volume.py b/appwrite/models/database_status_volume.py index 0b14ba8c..654b089a 100644 --- a/appwrite/models/database_status_volume.py +++ b/appwrite/models/database_status_volume.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DatabaseStatusVolume(AppwriteModel): """ Volume @@ -18,6 +19,7 @@ class DatabaseStatusVolume(AppwriteModel): mounted : bool Whether the volume is mounted. """ + path: str = Field(..., alias='path') usedpercent: str = Field(..., alias='usedPercent') available: str = Field(..., alias='available') diff --git a/appwrite/models/dedicated_database.py b/appwrite/models/dedicated_database.py index 810fe7df..dcc072e3 100644 --- a/appwrite/models/dedicated_database.py +++ b/appwrite/models/dedicated_database.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DedicatedDatabase(AppwriteModel): """ DedicatedDatabase @@ -106,6 +107,7 @@ class DedicatedDatabase(AppwriteModel): error : str Error message if status is failed. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/dedicated_database_backup.py b/appwrite/models/dedicated_database_backup.py new file mode 100644 index 00000000..40d47365 --- /dev/null +++ b/appwrite/models/dedicated_database_backup.py @@ -0,0 +1,65 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabaseBackup(AppwriteModel): + """ + Backup + + Attributes + ---------- + id : str + Backup ID. + createdat : str + Backup creation time in ISO 8601 format. + databaseid : str + Database ID this backup belongs to. + projectid : str + Project ID. + policyid : str + Backup policy ID when the backup was created by a schedule. + trigger : str + Backup trigger. Possible values: manual, schedule. + type : str + Backup type. Possible values: full (complete database snapshot), incremental (changes since last backup), wal (write-ahead log continuous archival). + requestedtype : str + Backup type that was requested. Differs from `type` when the backend could not run the requested type and took a different one instead, in which case `fallbackReason` explains why. Empty for backups taken before the requested type was recorded. + fallbackreason : str + Why the backend ran a different backup type than the one requested. Empty when the backup ran as requested. + status : str + Backup status. Possible values: pending (queued for processing), running (currently in progress), completed (successfully finished), failed (encountered an error), verified (integrity check passed). + sizebytes : float + Backup size in bytes. + startedat : Optional[str] + Backup start time in ISO 8601 format. + completedat : Optional[str] + Backup completion time in ISO 8601 format. + verifiedat : Optional[str] + Backup verification time in ISO 8601 format. + expiresat : Optional[str] + Backup expiration time in ISO 8601 format. + logposition : Optional[str] + Transaction-log position the backup anchors at, in the engine's own notation: PostgreSQL `{walSegment}|{lsn}`, MySQL and MariaDB `{binlogFile}|{offset}`, MongoDB `{seconds}|{increment}`. Empty when the backup recorded no position, which is the case for backup types that carry none. + error : str + Error message if backup failed. + """ + + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + databaseid: str = Field(..., alias='databaseId') + projectid: str = Field(..., alias='projectId') + policyid: str = Field(..., alias='policyId') + trigger: str = Field(..., alias='trigger') + type: str = Field(..., alias='type') + requestedtype: str = Field(..., alias='requestedType') + fallbackreason: str = Field(..., alias='fallbackReason') + status: str = Field(..., alias='status') + sizebytes: float = Field(..., alias='sizeBytes') + startedat: Optional[str] = Field(default=None, alias='startedAt') + completedat: Optional[str] = Field(default=None, alias='completedAt') + verifiedat: Optional[str] = Field(default=None, alias='verifiedAt') + expiresat: Optional[str] = Field(default=None, alias='expiresAt') + logposition: Optional[str] = Field(default=None, alias='logPosition') + error: str = Field(..., alias='error') diff --git a/appwrite/models/dedicated_database_backup_list.py b/appwrite/models/dedicated_database_backup_list.py new file mode 100644 index 00000000..d8d98696 --- /dev/null +++ b/appwrite/models/dedicated_database_backup_list.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_backup import DedicatedDatabaseBackup + + +class DedicatedDatabaseBackupList(AppwriteModel): + """ + BackupList + + Attributes + ---------- + total : float + Total number of backups. + backups : List[DedicatedDatabaseBackup] + List of backups. + """ + + total: float = Field(..., alias='total') + backups: List[DedicatedDatabaseBackup] = Field(..., alias='backups') diff --git a/appwrite/models/dedicated_database_backup_storage.py b/appwrite/models/dedicated_database_backup_storage.py new file mode 100644 index 00000000..039750c7 --- /dev/null +++ b/appwrite/models/dedicated_database_backup_storage.py @@ -0,0 +1,29 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabaseBackupStorage(AppwriteModel): + """ + BackupStorageConfig + + Attributes + ---------- + provider : str + Storage provider. Possible values: s3 (Amazon S3 or S3-compatible), gcs (Google Cloud Storage), azure (Azure Blob Storage). + bucket : str + Storage bucket or container name. + region : str + Storage region. + prefix : str + Object key prefix for backups. + endpoint : str + Custom endpoint for S3-compatible storage. + """ + + provider: str = Field(..., alias='provider') + bucket: str = Field(..., alias='bucket') + region: str = Field(..., alias='region') + prefix: str = Field(..., alias='prefix') + endpoint: str = Field(..., alias='endpoint') diff --git a/appwrite/models/dedicated_database_branch.py b/appwrite/models/dedicated_database_branch.py new file mode 100644 index 00000000..4699ab6a --- /dev/null +++ b/appwrite/models/dedicated_database_branch.py @@ -0,0 +1,50 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabaseBranch(AppwriteModel): + """ + Branch + + Attributes + ---------- + branchid : str + Branch identifier. + branchname : str + Branch name. + namespace : str + Kubernetes namespace where the branch is deployed. + expiresat : float + Unix timestamp when the branch expires. + host : str + Branch hostname for direct connections. + port : float + Branch port. Null until the backing reports one. + database : str + Advertised catalog the client connects to. MySQL/MariaDB use default; Postgres uses the routing label. + username : str + Database username. Shared with the parent database. + password : str + Database password. Shared with the parent database. + ssl : bool + Whether SSL is required. + engine : str + Database engine. Possible values: postgresql, mysql, mongodb. + connectionstring : str + Full connection string for the branch. + """ + + branchid: str = Field(..., alias='branchId') + branchname: str = Field(..., alias='branchName') + namespace: str = Field(..., alias='namespace') + expiresat: float = Field(..., alias='expiresAt') + host: str = Field(..., alias='host') + port: float = Field(..., alias='port') + database: str = Field(..., alias='database') + username: str = Field(..., alias='username') + password: str = Field(..., alias='password') + ssl: bool = Field(..., alias='ssl') + engine: str = Field(..., alias='engine') + connectionstring: str = Field(..., alias='connectionString') diff --git a/appwrite/models/dedicated_database_branch_list.py b/appwrite/models/dedicated_database_branch_list.py new file mode 100644 index 00000000..9966ba57 --- /dev/null +++ b/appwrite/models/dedicated_database_branch_list.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_branch import DedicatedDatabaseBranch + + +class DedicatedDatabaseBranchList(AppwriteModel): + """ + BranchList + + Attributes + ---------- + total : float + Total number of branches. + branches : List[DedicatedDatabaseBranch] + List of branches. + """ + + total: float = Field(..., alias='total') + branches: List[DedicatedDatabaseBranch] = Field(..., alias='branches') diff --git a/appwrite/models/dedicated_database_execution.py b/appwrite/models/dedicated_database_execution.py new file mode 100644 index 00000000..4a9a5eda --- /dev/null +++ b/appwrite/models/dedicated_database_execution.py @@ -0,0 +1,33 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_execution_column import DedicatedDatabaseExecutionColumn + + +class DedicatedDatabaseExecution(AppwriteModel): + """ + Execution + + Attributes + ---------- + rows : List[Any] + Result rows as a list of column-name => value maps. Empty for non-returning statements. + rowcount : float + Number of rows returned (for SELECT) or affected (for INSERT/UPDATE/DELETE). + columns : List[DedicatedDatabaseExecutionColumn] + Column metadata in result-set order. + durationms : float + Server-side execution time in milliseconds. + truncated : bool + True when the configured row or byte cap was hit and the result was truncated. + bytes : float + Serialised payload size in bytes. + """ + + rows: List[Any] = Field(..., alias='rows') + rowcount: float = Field(..., alias='rowCount') + columns: List[DedicatedDatabaseExecutionColumn] = Field(..., alias='columns') + durationms: float = Field(..., alias='durationMs') + truncated: bool = Field(..., alias='truncated') + bytes: float = Field(..., alias='bytes') diff --git a/appwrite/models/dedicated_database_execution_column.py b/appwrite/models/dedicated_database_execution_column.py new file mode 100644 index 00000000..095e7e59 --- /dev/null +++ b/appwrite/models/dedicated_database_execution_column.py @@ -0,0 +1,20 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabaseExecutionColumn(AppwriteModel): + """ + ExecutionColumn + + Attributes + ---------- + name : str + Column name as returned by the database. + type : str + Engine-specific column type (e.g. int4, text, timestamptz). + """ + + name: str = Field(..., alias='name') + type: str = Field(..., alias='type') diff --git a/appwrite/models/dedicated_database_extensions.py b/appwrite/models/dedicated_database_extensions.py new file mode 100644 index 00000000..363e6374 --- /dev/null +++ b/appwrite/models/dedicated_database_extensions.py @@ -0,0 +1,24 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .postgres_extension import PostgresExtension + + +class DedicatedDatabaseExtensions(AppwriteModel): + """ + Extensions + + Attributes + ---------- + installed : List[Any] + List of installed extensions. + available : List[Any] + List of available extensions that can be installed. + metadata : List[PostgresExtension] + Curated metadata (display name, description, category) for each available extension. + """ + + installed: List[Any] = Field(..., alias='installed') + available: List[Any] = Field(..., alias='available') + metadata: List[PostgresExtension] = Field(..., alias='metadata') diff --git a/appwrite/models/dedicated_database_list.py b/appwrite/models/dedicated_database_list.py new file mode 100644 index 00000000..f7e50415 --- /dev/null +++ b/appwrite/models/dedicated_database_list.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database import DedicatedDatabase + + +class DedicatedDatabaseList(AppwriteModel): + """ + Dedicated databases list + + Attributes + ---------- + total : float + Total number of databases that matched your query. + databases : List[DedicatedDatabase] + List of databases. + """ + + total: float = Field(..., alias='total') + databases: List[DedicatedDatabase] = Field(..., alias='databases') diff --git a/appwrite/models/dedicated_database_member.py b/appwrite/models/dedicated_database_member.py index 128021bb..55426f3f 100644 --- a/appwrite/models/dedicated_database_member.py +++ b/appwrite/models/dedicated_database_member.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DedicatedDatabaseMember(AppwriteModel): """ Member @@ -15,10 +16,14 @@ class DedicatedDatabaseMember(AppwriteModel): Member role. Possible values: primary (accepts reads and writes), replica (read-only follower), unknown (placement not established; reported while a transition is moving or restarting the topology and this member has not been probed, so no member can be named the write target). status : str Member pod status. Possible values: pending (configured but absent from the backend topology, so nothing is bringing it up), provisioning (pod missing or Pending), starting (Running but not Ready), active (Running and Ready), failed (Failed phase or CrashLoopBackOff container), or the lowercased pod phase reported by the cluster. + replicating : Optional[bool] + Whether the engine reports this member's replication stream as up. Null when no reading was taken: a primary has no stream to report, and a member that is not active, or whose probe did not answer, has none yet. False is a reading and null is the absence of one, so the two are not interchangeable. Read it beside lagSeconds before expecting a failover that names no target to find a promotable standby: a member streaming at a known lag is one, and a member reporting null is not evidence either way. lagseconds : Optional[float] - Replication lag in seconds. Null when the lag is not known: a primary has none to report, and a member the backend has not probed has none yet. + Replication lag in seconds. Null when the lag is not known: a primary has none to report, and a member the backend has not probed has none yet. Also null against `replicating: true`, for a member that is streaming but whose engine printed no numeric lag. """ + id: str = Field(..., alias='$id') role: str = Field(..., alias='role') status: str = Field(..., alias='status') + replicating: Optional[bool] = Field(default=None, alias='replicating') lagseconds: Optional[float] = Field(default=None, alias='lagSeconds') diff --git a/appwrite/models/dedicated_database_operation.py b/appwrite/models/dedicated_database_operation.py index 97d482d3..3a6c29a9 100644 --- a/appwrite/models/dedicated_database_operation.py +++ b/appwrite/models/dedicated_database_operation.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DedicatedDatabaseOperation(AppwriteModel): """ Operation @@ -18,7 +19,7 @@ class DedicatedDatabaseOperation(AppwriteModel): type : str Operation type, such as provision, update, restore, pausing, resuming, failover, backup-create or cross-region-enable. status : str - Operation status. Possible values: running (in progress), completed (finished successfully), failed (ended in an error). + Operation status. Possible values: queued (accepted and waiting to resume), running (in progress), completed (finished successfully), failed (ended in an error). attempts : float Number of times this operation has been attempted. requestedat : Optional[str] @@ -32,6 +33,7 @@ class DedicatedDatabaseOperation(AppwriteModel): errormessage : str Failure message if the operation failed. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') databaseid: str = Field(..., alias='databaseId') diff --git a/appwrite/models/dedicated_database_operation_list.py b/appwrite/models/dedicated_database_operation_list.py index 012e21d5..30d2cc8c 100644 --- a/appwrite/models/dedicated_database_operation_list.py +++ b/appwrite/models/dedicated_database_operation_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .dedicated_database_operation import DedicatedDatabaseOperation + class DedicatedDatabaseOperationList(AppwriteModel): """ OperationList @@ -15,5 +16,6 @@ class DedicatedDatabaseOperationList(AppwriteModel): operations : List[DedicatedDatabaseOperation] List of operations. """ + total: float = Field(..., alias='total') operations: List[DedicatedDatabaseOperation] = Field(..., alias='operations') diff --git a/appwrite/models/dedicated_database_pitr_windows.py b/appwrite/models/dedicated_database_pitr_windows.py new file mode 100644 index 00000000..243710e6 --- /dev/null +++ b/appwrite/models/dedicated_database_pitr_windows.py @@ -0,0 +1,20 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabasePITRWindows(AppwriteModel): + """ + PITRWindows + + Attributes + ---------- + earliest : str + Earliest available recovery point. + latest : str + Latest available recovery point. + """ + + earliest: str = Field(..., alias='earliest') + latest: str = Field(..., alias='latest') diff --git a/appwrite/models/dedicated_database_pooler.py b/appwrite/models/dedicated_database_pooler.py new file mode 100644 index 00000000..3316d96f --- /dev/null +++ b/appwrite/models/dedicated_database_pooler.py @@ -0,0 +1,44 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabasePooler(AppwriteModel): + """ + PoolerConfig + + Attributes + ---------- + enabled : bool + Whether connection pooling is enabled. + mode : str + Connection pool mode. Possible values: transaction (releases connections back to pool after each transaction), session (holds connections for the entire client session). + maxconnections : float + Client-connection ceiling the pooler accepts. Enforced on MySQL and MariaDB; on PostgreSQL the pooler has no client cap, so this reports the database's advertised networkMaxConnections and cannot be set here. + defaultpoolsize : float + Default pool size per user. + port : float + Pooler listening port. + readwritesplitting : bool + Whether SELECTs are routed to HA replicas while writes and locked reads stay on the primary. Active only when HA is enabled. + poolercpurequest : str + Effective CPU request applied to the pooler sidecar container (Kubernetes quantity). Returns the proportional default (5% of DB CPU, floor 100m) unless overridden. + poolercpulimit : str + Effective CPU limit applied to the pooler sidecar container (Kubernetes quantity). Returns the proportional default (10% of DB CPU, floor 200m) unless overridden. + poolermemoryrequest : str + Effective memory request applied to the pooler sidecar container (Kubernetes quantity). Returns the proportional default (7.5% of DB memory, floor 64Mi) unless overridden. + poolermemorylimit : str + Effective memory limit applied to the pooler sidecar container (Kubernetes quantity). Returns the proportional default (15% of DB memory, floor 128Mi) unless overridden. + """ + + enabled: bool = Field(..., alias='enabled') + mode: str = Field(..., alias='mode') + maxconnections: float = Field(..., alias='maxConnections') + defaultpoolsize: float = Field(..., alias='defaultPoolSize') + port: float = Field(..., alias='port') + readwritesplitting: bool = Field(..., alias='readWriteSplitting') + poolercpurequest: str = Field(..., alias='poolerCpuRequest') + poolercpulimit: str = Field(..., alias='poolerCpuLimit') + poolermemoryrequest: str = Field(..., alias='poolerMemoryRequest') + poolermemorylimit: str = Field(..., alias='poolerMemoryLimit') diff --git a/appwrite/models/dedicated_database_replicas.py b/appwrite/models/dedicated_database_replicas.py index 45e6de40..fc035b2b 100644 --- a/appwrite/models/dedicated_database_replicas.py +++ b/appwrite/models/dedicated_database_replicas.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .dedicated_database_member import DedicatedDatabaseMember + class DedicatedDatabaseReplicas(AppwriteModel): """ Replicas @@ -27,6 +28,7 @@ class DedicatedDatabaseReplicas(AppwriteModel): members : List[DedicatedDatabaseMember] Per-pod statuses for the primary and every replica. """ + replicas: float = Field(..., alias='replicas') syncmode: str = Field(..., alias='syncMode') effectivesyncmode: Optional[str] = Field(default=None, alias='effectiveSyncMode') diff --git a/appwrite/models/dedicated_database_restoration.py b/appwrite/models/dedicated_database_restoration.py new file mode 100644 index 00000000..7965c50d --- /dev/null +++ b/appwrite/models/dedicated_database_restoration.py @@ -0,0 +1,50 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class DedicatedDatabaseRestoration(AppwriteModel): + """ + Restoration + + Attributes + ---------- + id : str + Restoration ID. + createdat : str + Restoration creation time in ISO 8601 format. + databaseid : str + Database ID being restored into. + sourcedatabaseid : str + Source database ID when restoring a backup into another database. + projectid : str + Project ID. + backupid : str + Backup ID used for restoration (null for PITR). + type : str + Restoration type. Possible values: backup (restore from a specific backup snapshot), pitr (point-in-time recovery to a specific timestamp). + status : str + Restoration status. Possible values: pending (queued for processing), running (currently in progress), completed (successfully finished), failed (encountered an error). + targettime : str + Target time for PITR restoration in ISO 8601 format. + startedat : str + Restoration start time in ISO 8601 format. + completedat : str + Restoration completion time in ISO 8601 format. + error : str + Error message if restoration failed. + """ + + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + databaseid: str = Field(..., alias='databaseId') + sourcedatabaseid: str = Field(..., alias='sourceDatabaseId') + projectid: str = Field(..., alias='projectId') + backupid: str = Field(..., alias='backupId') + type: str = Field(..., alias='type') + status: str = Field(..., alias='status') + targettime: str = Field(..., alias='targetTime') + startedat: str = Field(..., alias='startedAt') + completedat: str = Field(..., alias='completedAt') + error: str = Field(..., alias='error') diff --git a/appwrite/models/dedicated_database_restoration_list.py b/appwrite/models/dedicated_database_restoration_list.py new file mode 100644 index 00000000..8eac8c70 --- /dev/null +++ b/appwrite/models/dedicated_database_restoration_list.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .dedicated_database_restoration import DedicatedDatabaseRestoration + + +class DedicatedDatabaseRestorationList(AppwriteModel): + """ + Dedicated database restorations list + + Attributes + ---------- + total : float + Total number of restorations that matched your query. + restorations : List[DedicatedDatabaseRestoration] + List of restorations. + """ + + total: float = Field(..., alias='total') + restorations: List[DedicatedDatabaseRestoration] = Field(..., alias='restorations') diff --git a/appwrite/models/dedicated_database_specification.py b/appwrite/models/dedicated_database_specification.py index d5f37295..71cf58fa 100644 --- a/appwrite/models/dedicated_database_specification.py +++ b/appwrite/models/dedicated_database_specification.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DedicatedDatabaseSpecification(AppwriteModel): """ Specification @@ -28,6 +29,7 @@ class DedicatedDatabaseSpecification(AppwriteModel): enabled : bool Whether the specification is available on the current plan. """ + slug: str = Field(..., alias='slug') name: str = Field(..., alias='name') price: float = Field(..., alias='price') diff --git a/appwrite/models/dedicated_database_specification_list.py b/appwrite/models/dedicated_database_specification_list.py index 8cbd905d..92c0b23f 100644 --- a/appwrite/models/dedicated_database_specification_list.py +++ b/appwrite/models/dedicated_database_specification_list.py @@ -5,6 +5,7 @@ from .dedicated_database_specification import DedicatedDatabaseSpecification from .dedicated_database_specification_pricing import DedicatedDatabaseSpecificationPricing + class DedicatedDatabaseSpecificationList(AppwriteModel): """ SpecificationList @@ -18,6 +19,7 @@ class DedicatedDatabaseSpecificationList(AppwriteModel): pricing : DedicatedDatabaseSpecificationPricing Overage and add-on pricing shared across all specifications. """ + specifications: List[DedicatedDatabaseSpecification] = Field(..., alias='specifications') total: float = Field(..., alias='total') pricing: DedicatedDatabaseSpecificationPricing = Field(..., alias='pricing') diff --git a/appwrite/models/dedicated_database_specification_pricing.py b/appwrite/models/dedicated_database_specification_pricing.py index 4c614a5a..83b03a6a 100644 --- a/appwrite/models/dedicated_database_specification_pricing.py +++ b/appwrite/models/dedicated_database_specification_pricing.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DedicatedDatabaseSpecificationPricing(AppwriteModel): """ SpecificationPricing @@ -18,6 +19,7 @@ class DedicatedDatabaseSpecificationPricing(AppwriteModel): pitrrate : float Point-in-time recovery price as a fraction of the specification cost. """ + storageoveragerate: float = Field(..., alias='storageOverageRate') bandwidthoveragerate: float = Field(..., alias='bandwidthOverageRate') replicarate: float = Field(..., alias='replicaRate') diff --git a/appwrite/models/deployment.py b/appwrite/models/deployment.py index 13c3f735..f4baf0c9 100644 --- a/appwrite/models/deployment.py +++ b/appwrite/models/deployment.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.deployment_status import DeploymentStatus + class Deployment(AppwriteModel): """ Deployment @@ -65,6 +66,7 @@ class Deployment(AppwriteModel): providerbranchurl : str The branch of the vcs repository """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/deployment_list.py b/appwrite/models/deployment_list.py index 6ed143c0..d3c435d9 100644 --- a/appwrite/models/deployment_list.py +++ b/appwrite/models/deployment_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .deployment import Deployment + class DeploymentList(AppwriteModel): """ Deployments List @@ -15,5 +16,6 @@ class DeploymentList(AppwriteModel): deployments : List[Deployment] List of deployments. """ + total: float = Field(..., alias='total') deployments: List[Deployment] = Field(..., alias='deployments') diff --git a/appwrite/models/dev_key.py b/appwrite/models/dev_key.py index b77acfd5..c36cf0f6 100644 --- a/appwrite/models/dev_key.py +++ b/appwrite/models/dev_key.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class DevKey(AppwriteModel): """ DevKey @@ -26,6 +27,7 @@ class DevKey(AppwriteModel): sdks : List[Any] List of SDK user agents that used this key. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/document.py b/appwrite/models/document.py index b0ae18f4..f59435f1 100644 --- a/appwrite/models/document.py +++ b/appwrite/models/document.py @@ -7,6 +7,7 @@ _PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Document(AppwriteModel, Generic[T]): """ Document @@ -28,6 +29,7 @@ class Document(AppwriteModel, Generic[T]): permissions : List[Any] Document permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). """ + id: str = Field(..., alias='$id') sequence: str = Field(..., alias='$sequence') collectionid: str = Field(..., alias='$collectionId') @@ -39,7 +41,15 @@ class Document(AppwriteModel, Generic[T]): @classmethod def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Document[T]': """Create Document instance with typed data.""" - internal_aliases = {'$id', '$sequence', '$collectionId', '$databaseId', '$createdAt', '$updatedAt', '$permissions'} + internal_aliases = { + '$id', + '$sequence', + '$collectionId', + '$databaseId', + '$createdAt', + '$updatedAt', + '$permissions', + } internal_fields = {k: v for k, v in data.items() if k in internal_aliases} user_data = {k: v for k, v in data.items() if k not in internal_aliases and k != 'data'} nested = data.get('data') diff --git a/appwrite/models/document_list.py b/appwrite/models/document_list.py index 728c8039..ff2045dc 100644 --- a/appwrite/models/document_list.py +++ b/appwrite/models/document_list.py @@ -6,6 +6,7 @@ T = TypeVar('T') + class DocumentList(AppwriteModel, Generic[T]): """ Documents List @@ -17,6 +18,7 @@ class DocumentList(AppwriteModel, Generic[T]): documents : List[Document[T]] List of documents. """ + total: float = Field(..., alias='total') documents: List[Document[T]] = Field(..., alias='documents') @@ -25,8 +27,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Documen """Create DocumentList instance with typed data.""" instance = cls.model_validate(data) if 'documents' in data and data['documents'] is not None: - instance.documents = [ - Document.with_data(row, model_type) - for row in data['documents'] - ] + instance.documents = [Document.with_data(row, model_type) for row in data['documents']] return instance diff --git a/appwrite/models/email_template.py b/appwrite/models/email_template.py index 87af0a74..302173e9 100644 --- a/appwrite/models/email_template.py +++ b/appwrite/models/email_template.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class EmailTemplate(AppwriteModel): """ EmailTemplate @@ -26,6 +27,7 @@ class EmailTemplate(AppwriteModel): subject : str Email subject """ + templateid: str = Field(..., alias='templateId') locale: str = Field(..., alias='locale') message: str = Field(..., alias='message') diff --git a/appwrite/models/email_template_list.py b/appwrite/models/email_template_list.py index 8bca9063..3a601e4a 100644 --- a/appwrite/models/email_template_list.py +++ b/appwrite/models/email_template_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .email_template import EmailTemplate + class EmailTemplateList(AppwriteModel): """ Email Templates List @@ -15,5 +16,6 @@ class EmailTemplateList(AppwriteModel): templates : List[EmailTemplate] List of templates. """ + total: float = Field(..., alias='total') templates: List[EmailTemplate] = Field(..., alias='templates') diff --git a/appwrite/models/embedding.py b/appwrite/models/embedding.py index 9da9bab5..c308479a 100644 --- a/appwrite/models/embedding.py +++ b/appwrite/models/embedding.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Embedding(AppwriteModel): """ Embedding @@ -18,6 +19,7 @@ class Embedding(AppwriteModel): error : str Error message if embedding generation fails. Empty string if no error. """ + model: str = Field(..., alias='model') dimension: float = Field(..., alias='dimension') embedding: List[Any] = Field(..., alias='embedding') diff --git a/appwrite/models/embedding_list.py b/appwrite/models/embedding_list.py index d8f437e7..afa3a12e 100644 --- a/appwrite/models/embedding_list.py +++ b/appwrite/models/embedding_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .embedding import Embedding + class EmbeddingList(AppwriteModel): """ Embedding list @@ -15,5 +16,6 @@ class EmbeddingList(AppwriteModel): embeddings : List[Embedding] List of embeddings. """ + total: float = Field(..., alias='total') embeddings: List[Embedding] = Field(..., alias='embeddings') diff --git a/appwrite/models/ephemeral_key.py b/appwrite/models/ephemeral_key.py index eeb976e3..ed21e512 100644 --- a/appwrite/models/ephemeral_key.py +++ b/appwrite/models/ephemeral_key.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class EphemeralKey(AppwriteModel): """ Ephemeral Key @@ -28,6 +29,7 @@ class EphemeralKey(AppwriteModel): sdks : List[Any] List of SDK user agents that used this key. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/execution.py b/appwrite/models/execution.py index eaf9a80a..37706152 100644 --- a/appwrite/models/execution.py +++ b/appwrite/models/execution.py @@ -2,10 +2,12 @@ from pydantic import Field, PrivateAttr from .base_model import AppwriteModel +from ..enums.execution_resource_type import ExecutionResourceType from ..enums.execution_trigger import ExecutionTrigger from ..enums.execution_status import ExecutionStatus from .headers import Headers + class Execution(AppwriteModel): """ Execution @@ -20,14 +22,16 @@ class Execution(AppwriteModel): Execution update date in ISO 8601 format. permissions : List[Any] Execution roles. - functionid : str - Function ID. + resourceid : str + Function or site ID. + resourcetype : ExecutionResourceType + Execution resource type. deploymentid : str - Function's deployment ID used to create the execution. + Deployment ID used to create the execution. trigger : ExecutionTrigger - The trigger that caused the function to execute. Possible values can be: `http`, `schedule`, or `event`. + The trigger that caused the resource to execute. Possible values can be: `http`, `schedule`, or `event`. status : ExecutionStatus - The status of the function execution. Possible values can be: `waiting`, `processing`, `completed`, `failed`, or `scheduled`. + The status of the resource execution. Possible values can be: `waiting`, `processing`, `completed`, `failed`, or `scheduled`. requestmethod : str HTTP request method type. requestpath : str @@ -41,19 +45,21 @@ class Execution(AppwriteModel): responseheaders : List[Headers] HTTP response headers as a key-value object. This will return only whitelisted headers. All headers are returned if execution is created as synchronous. logs : str - Function logs. Includes the last 4,000 characters. This will return an empty string unless the response is returned using an API key or as part of a webhook payload. + Resource logs. Includes the last 4,000 characters. This will return an empty string unless the response is returned using an API key or as part of a webhook payload. errors : str - Function errors. Includes the last 4,000 characters. This will return an empty string unless the response is returned using an API key or as part of a webhook payload. + Resource errors. Includes the last 4,000 characters. This will return an empty string unless the response is returned using an API key or as part of a webhook payload. duration : float Resource(function/site) execution duration in seconds. scheduledat : Optional[str] The scheduled time for execution. If left empty, execution will be queued immediately. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') permissions: List[Any] = Field(..., alias='$permissions') - functionid: str = Field(..., alias='functionId') + resourceid: str = Field(..., alias='resourceId') + resourcetype: ExecutionResourceType = Field(..., alias='resourceType') deploymentid: str = Field(..., alias='deploymentId') trigger: ExecutionTrigger = Field(..., alias='trigger') status: ExecutionStatus = Field(..., alias='status') diff --git a/appwrite/models/execution_list.py b/appwrite/models/execution_list.py index 3d336d25..a3adbe24 100644 --- a/appwrite/models/execution_list.py +++ b/appwrite/models/execution_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .execution import Execution + class ExecutionList(AppwriteModel): """ Executions List @@ -15,5 +16,6 @@ class ExecutionList(AppwriteModel): executions : List[Execution] List of executions. """ + total: float = Field(..., alias='total') executions: List[Execution] = Field(..., alias='executions') diff --git a/appwrite/models/file.py b/appwrite/models/file.py index 3657b451..dbf040c8 100644 --- a/appwrite/models/file.py +++ b/appwrite/models/file.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class File(AppwriteModel): """ File @@ -42,6 +43,7 @@ class File(AppwriteModel): compression : str Compression algorithm used for the file. Will be one of none, [gzip](https://en.wikipedia.org/wiki/Gzip), or [zstd](https://en.wikipedia.org/wiki/Zstd). """ + id: str = Field(..., alias='$id') bucketid: str = Field(..., alias='bucketId') createdat: str = Field(..., alias='$createdAt') diff --git a/appwrite/models/file_list.py b/appwrite/models/file_list.py index 4ab21cdc..c5166525 100644 --- a/appwrite/models/file_list.py +++ b/appwrite/models/file_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .file import File + class FileList(AppwriteModel): """ Files List @@ -15,5 +16,6 @@ class FileList(AppwriteModel): files : List[File] List of files. """ + total: float = Field(..., alias='total') files: List[File] = Field(..., alias='files') diff --git a/appwrite/models/framework.py b/appwrite/models/framework.py index 6bfe7598..f9fc73d2 100644 --- a/appwrite/models/framework.py +++ b/appwrite/models/framework.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .framework_adapter import FrameworkAdapter + class Framework(AppwriteModel): """ Framework @@ -21,6 +22,7 @@ class Framework(AppwriteModel): adapters : List[FrameworkAdapter] List of supported adapters. """ + key: str = Field(..., alias='key') name: str = Field(..., alias='name') buildruntime: str = Field(..., alias='buildRuntime') diff --git a/appwrite/models/framework_adapter.py b/appwrite/models/framework_adapter.py index e7c567f8..e2ed9299 100644 --- a/appwrite/models/framework_adapter.py +++ b/appwrite/models/framework_adapter.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class FrameworkAdapter(AppwriteModel): """ Framework Adapter @@ -20,6 +21,7 @@ class FrameworkAdapter(AppwriteModel): fallbackfile : str Name of fallback file to use instead of 404 page. If null, Appwrite 404 page will be displayed. """ + key: str = Field(..., alias='key') installcommand: str = Field(..., alias='installCommand') buildcommand: str = Field(..., alias='buildCommand') diff --git a/appwrite/models/framework_list.py b/appwrite/models/framework_list.py index 60ec6b4c..47ab1244 100644 --- a/appwrite/models/framework_list.py +++ b/appwrite/models/framework_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .framework import Framework + class FrameworkList(AppwriteModel): """ Frameworks List @@ -15,5 +16,6 @@ class FrameworkList(AppwriteModel): frameworks : List[Framework] List of frameworks. """ + total: float = Field(..., alias='total') frameworks: List[Framework] = Field(..., alias='frameworks') diff --git a/appwrite/models/function.py b/appwrite/models/function.py index 6e3dd16a..052018fa 100644 --- a/appwrite/models/function.py +++ b/appwrite/models/function.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .variable import Variable + class Function(AppwriteModel): """ Function @@ -75,6 +76,7 @@ class Function(AppwriteModel): runtimespecification : str Machine specification for executions. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/function_list.py b/appwrite/models/function_list.py index 2beb1e81..ec302b07 100644 --- a/appwrite/models/function_list.py +++ b/appwrite/models/function_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .function import Function + class FunctionList(AppwriteModel): """ Functions List @@ -15,5 +16,6 @@ class FunctionList(AppwriteModel): functions : List[Function] List of functions. """ + total: float = Field(..., alias='total') functions: List[Function] = Field(..., alias='functions') diff --git a/appwrite/models/headers.py b/appwrite/models/headers.py index 6775537e..569f2e9f 100644 --- a/appwrite/models/headers.py +++ b/appwrite/models/headers.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Headers(AppwriteModel): """ Headers @@ -14,5 +15,6 @@ class Headers(AppwriteModel): value : str Header value. """ + name: str = Field(..., alias='name') value: str = Field(..., alias='value') diff --git a/appwrite/models/identity.py b/appwrite/models/identity.py index 4f5ab568..c5ff2655 100644 --- a/appwrite/models/identity.py +++ b/appwrite/models/identity.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Identity(AppwriteModel): """ Identity @@ -30,6 +31,7 @@ class Identity(AppwriteModel): providerrefreshtoken : str Identity Provider Refresh Token. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/identity_list.py b/appwrite/models/identity_list.py index 02abfdf3..ced73450 100644 --- a/appwrite/models/identity_list.py +++ b/appwrite/models/identity_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .identity import Identity + class IdentityList(AppwriteModel): """ Identities List @@ -15,5 +16,6 @@ class IdentityList(AppwriteModel): identities : List[Identity] List of identities. """ + total: float = Field(..., alias='total') identities: List[Identity] = Field(..., alias='identities') diff --git a/appwrite/models/index.py b/appwrite/models/index.py index 9fc6d031..aea86c9f 100644 --- a/appwrite/models/index.py +++ b/appwrite/models/index.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.index_status import IndexStatus + class Index(AppwriteModel): """ Index @@ -31,6 +32,7 @@ class Index(AppwriteModel): orders : Optional[List[Any]] Index orders. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/index_list.py b/appwrite/models/index_list.py index a0984a7a..b9eeab2c 100644 --- a/appwrite/models/index_list.py +++ b/appwrite/models/index_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .index import Index + class IndexList(AppwriteModel): """ Indexes List @@ -15,5 +16,6 @@ class IndexList(AppwriteModel): indexes : List[Index] List of indexes. """ + total: float = Field(..., alias='total') indexes: List[Index] = Field(..., alias='indexes') diff --git a/appwrite/models/insight.py b/appwrite/models/insight.py index d0d263b9..8c561228 100644 --- a/appwrite/models/insight.py +++ b/appwrite/models/insight.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .insight_cta import InsightCTA + class Insight(AppwriteModel): """ Insight @@ -45,6 +46,7 @@ class Insight(AppwriteModel): dismissedby : Optional[str] User ID that dismissed the insight. Empty when not dismissed. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/insight_cta.py b/appwrite/models/insight_cta.py index 2c74929b..bc4144f7 100644 --- a/appwrite/models/insight_cta.py +++ b/appwrite/models/insight_cta.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class InsightCTA(AppwriteModel): """ InsightCTA @@ -18,6 +19,7 @@ class InsightCTA(AppwriteModel): params : Dict[str, Any] Parameter map the client should pass to the service method when this CTA is triggered. Keys match the target API's parameter names (e.g. databaseId/tableId/columns for tablesDB, databaseId/collectionId/attributes for the legacy Databases API). """ + label: str = Field(..., alias='label') service: str = Field(..., alias='service') method: str = Field(..., alias='method') diff --git a/appwrite/models/insight_list.py b/appwrite/models/insight_list.py index 4837a3d0..1ac76409 100644 --- a/appwrite/models/insight_list.py +++ b/appwrite/models/insight_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .insight import Insight + class InsightList(AppwriteModel): """ Insights List @@ -15,5 +16,6 @@ class InsightList(AppwriteModel): insights : List[Insight] List of insights. """ + total: float = Field(..., alias='total') insights: List[Insight] = Field(..., alias='insights') diff --git a/appwrite/models/jwt.py b/appwrite/models/jwt.py index b68dd3d3..4887d305 100644 --- a/appwrite/models/jwt.py +++ b/appwrite/models/jwt.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Jwt(AppwriteModel): """ JWT @@ -12,4 +13,5 @@ class Jwt(AppwriteModel): jwt : str JWT encoded string. """ + jwt: str = Field(..., alias='jwt') diff --git a/appwrite/models/key.py b/appwrite/models/key.py index 2d148d5c..b47526d9 100644 --- a/appwrite/models/key.py +++ b/appwrite/models/key.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Key(AppwriteModel): """ Key @@ -28,6 +29,7 @@ class Key(AppwriteModel): sdks : List[Any] List of SDK user agents that used this key. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/key_list.py b/appwrite/models/key_list.py index 2512608b..067da645 100644 --- a/appwrite/models/key_list.py +++ b/appwrite/models/key_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .key import Key + class KeyList(AppwriteModel): """ API Keys List @@ -15,5 +16,6 @@ class KeyList(AppwriteModel): keys : List[Key] List of keys. """ + total: float = Field(..., alias='total') keys: List[Key] = Field(..., alias='keys') diff --git a/appwrite/models/language.py b/appwrite/models/language.py index 77381266..15f23e53 100644 --- a/appwrite/models/language.py +++ b/appwrite/models/language.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Language(AppwriteModel): """ Language @@ -16,6 +17,7 @@ class Language(AppwriteModel): nativename : str Language native name. """ + name: str = Field(..., alias='name') code: str = Field(..., alias='code') nativename: str = Field(..., alias='nativeName') diff --git a/appwrite/models/language_list.py b/appwrite/models/language_list.py index 815ef98c..2e3ff697 100644 --- a/appwrite/models/language_list.py +++ b/appwrite/models/language_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .language import Language + class LanguageList(AppwriteModel): """ Languages List @@ -15,5 +16,6 @@ class LanguageList(AppwriteModel): languages : List[Language] List of languages. """ + total: float = Field(..., alias='total') languages: List[Language] = Field(..., alias='languages') diff --git a/appwrite/models/locale.py b/appwrite/models/locale.py index f8aa6de8..8d9cef21 100644 --- a/appwrite/models/locale.py +++ b/appwrite/models/locale.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Locale(AppwriteModel): """ Locale @@ -46,6 +47,7 @@ class Locale(AppwriteModel): connectionorganization : Optional[str] Registered organization of the IP """ + ip: str = Field(..., alias='ip') countrycode: str = Field(..., alias='countryCode') country: str = Field(..., alias='country') diff --git a/appwrite/models/locale_code.py b/appwrite/models/locale_code.py index 5e845f45..5381c5ec 100644 --- a/appwrite/models/locale_code.py +++ b/appwrite/models/locale_code.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class LocaleCode(AppwriteModel): """ LocaleCode @@ -14,5 +15,6 @@ class LocaleCode(AppwriteModel): name : str Locale name """ + code: str = Field(..., alias='code') name: str = Field(..., alias='name') diff --git a/appwrite/models/locale_code_list.py b/appwrite/models/locale_code_list.py index c4118a3e..c80ce4ad 100644 --- a/appwrite/models/locale_code_list.py +++ b/appwrite/models/locale_code_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .locale_code import LocaleCode + class LocaleCodeList(AppwriteModel): """ Locale codes list @@ -15,5 +16,6 @@ class LocaleCodeList(AppwriteModel): localecodes : List[LocaleCode] List of localeCodes. """ + total: float = Field(..., alias='total') localecodes: List[LocaleCode] = Field(..., alias='localeCodes') diff --git a/appwrite/models/log.py b/appwrite/models/log.py index 6824028e..a3b74c15 100644 --- a/appwrite/models/log.py +++ b/appwrite/models/log.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Log(AppwriteModel): """ Log @@ -54,6 +55,7 @@ class Log(AppwriteModel): countryname : str Country name. """ + event: str = Field(..., alias='event') userid: str = Field(..., alias='userId') useremail: str = Field(..., alias='userEmail') diff --git a/appwrite/models/log_list.py b/appwrite/models/log_list.py index 5eb09402..33ff6c77 100644 --- a/appwrite/models/log_list.py +++ b/appwrite/models/log_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .log import Log + class LogList(AppwriteModel): """ Logs List @@ -15,5 +16,6 @@ class LogList(AppwriteModel): logs : List[Log] List of logs. """ + total: float = Field(..., alias='total') logs: List[Log] = Field(..., alias='logs') diff --git a/appwrite/models/membership.py b/appwrite/models/membership.py index 83b276cc..173096ce 100644 --- a/appwrite/models/membership.py +++ b/appwrite/models/membership.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Membership(AppwriteModel): """ Membership @@ -40,6 +41,7 @@ class Membership(AppwriteModel): roles : List[Any] User list of roles """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/membership_list.py b/appwrite/models/membership_list.py index 4ac7aa35..19f23189 100644 --- a/appwrite/models/membership_list.py +++ b/appwrite/models/membership_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .membership import Membership + class MembershipList(AppwriteModel): """ Memberships List @@ -15,5 +16,6 @@ class MembershipList(AppwriteModel): memberships : List[Membership] List of memberships. """ + total: float = Field(..., alias='total') memberships: List[Membership] = Field(..., alias='memberships') diff --git a/appwrite/models/message.py b/appwrite/models/message.py index e1189c4d..6662583f 100644 --- a/appwrite/models/message.py +++ b/appwrite/models/message.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.message_status import MessageStatus + class Message(AppwriteModel): """ Message @@ -37,6 +38,7 @@ class Message(AppwriteModel): status : MessageStatus Status of delivery. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/message_list.py b/appwrite/models/message_list.py index 87513c88..ffea3f8f 100644 --- a/appwrite/models/message_list.py +++ b/appwrite/models/message_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .message import Message + class MessageList(AppwriteModel): """ Message list @@ -15,5 +16,6 @@ class MessageList(AppwriteModel): messages : List[Message] List of messages. """ + total: float = Field(..., alias='total') messages: List[Message] = Field(..., alias='messages') diff --git a/appwrite/models/mfa_challenge.py b/appwrite/models/mfa_challenge.py index c05ec3dd..5ad1ec9c 100644 --- a/appwrite/models/mfa_challenge.py +++ b/appwrite/models/mfa_challenge.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MfaChallenge(AppwriteModel): """ MFA Challenge @@ -18,6 +19,7 @@ class MfaChallenge(AppwriteModel): expire : str Token expiration date in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') userid: str = Field(..., alias='userId') diff --git a/appwrite/models/mfa_challenge_secret.py b/appwrite/models/mfa_challenge_secret.py index 89beb284..e9a03fb1 100644 --- a/appwrite/models/mfa_challenge_secret.py +++ b/appwrite/models/mfa_challenge_secret.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MfaChallengeSecret(AppwriteModel): """ MFA Challenge Secret @@ -20,6 +21,7 @@ class MfaChallengeSecret(AppwriteModel): code : str Challenge code to be delivered to the end user through a custom channel. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') userid: str = Field(..., alias='userId') diff --git a/appwrite/models/mfa_factors.py b/appwrite/models/mfa_factors.py index 2d6953a1..24810f03 100644 --- a/appwrite/models/mfa_factors.py +++ b/appwrite/models/mfa_factors.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MfaFactors(AppwriteModel): """ MFAFactors @@ -20,6 +21,7 @@ class MfaFactors(AppwriteModel): custom : bool Can custom factor be used for MFA challenge for this account. """ + totp: bool = Field(..., alias='totp') phone: bool = Field(..., alias='phone') email: bool = Field(..., alias='email') diff --git a/appwrite/models/mfa_recovery_codes.py b/appwrite/models/mfa_recovery_codes.py index a9f6491a..e64bf853 100644 --- a/appwrite/models/mfa_recovery_codes.py +++ b/appwrite/models/mfa_recovery_codes.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MfaRecoveryCodes(AppwriteModel): """ MFA Recovery Codes @@ -12,4 +13,5 @@ class MfaRecoveryCodes(AppwriteModel): recoverycodes : List[Any] Recovery codes. """ + recoverycodes: List[Any] = Field(..., alias='recoveryCodes') diff --git a/appwrite/models/mfa_type.py b/appwrite/models/mfa_type.py index a24ea219..5d6bb5e9 100644 --- a/appwrite/models/mfa_type.py +++ b/appwrite/models/mfa_type.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MfaType(AppwriteModel): """ MFAType @@ -14,5 +15,6 @@ class MfaType(AppwriteModel): uri : str URI for authenticator apps. """ + secret: str = Field(..., alias='secret') uri: str = Field(..., alias='uri') diff --git a/appwrite/models/mock_number.py b/appwrite/models/mock_number.py index 30348833..9e6f09cc 100644 --- a/appwrite/models/mock_number.py +++ b/appwrite/models/mock_number.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class MockNumber(AppwriteModel): """ Mock Number @@ -12,12 +13,13 @@ class MockNumber(AppwriteModel): number : str Mock phone number for testing phone authentication. Useful for testing phone authentication without sending an SMS. otp : str - Mock OTP for the number. + Mock OTP for the number. createdat : str Attribute creation date in ISO 8601 format. updatedat : str Attribute update date in ISO 8601 format. """ + number: str = Field(..., alias='number') otp: str = Field(..., alias='otp') createdat: str = Field(..., alias='$createdAt') diff --git a/appwrite/models/mock_number_list.py b/appwrite/models/mock_number_list.py index 6f11a81b..ae29efe9 100644 --- a/appwrite/models/mock_number_list.py +++ b/appwrite/models/mock_number_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .mock_number import MockNumber + class MockNumberList(AppwriteModel): """ Mock Numbers List @@ -15,5 +16,6 @@ class MockNumberList(AppwriteModel): mocknumbers : List[MockNumber] List of mockNumbers. """ + total: float = Field(..., alias='total') mocknumbers: List[MockNumber] = Field(..., alias='mockNumbers') diff --git a/appwrite/models/o_auth2_amazon.py b/appwrite/models/o_auth2_amazon.py index 6d0e2977..aad2ebb3 100644 --- a/appwrite/models/o_auth2_amazon.py +++ b/appwrite/models/o_auth2_amazon.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Amazon(AppwriteModel): """ OAuth2Amazon @@ -18,6 +19,7 @@ class OAuth2Amazon(AppwriteModel): clientsecret : str Amazon OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_apple.py b/appwrite/models/o_auth2_apple.py index 85096a79..e5f2e488 100644 --- a/appwrite/models/o_auth2_apple.py +++ b/appwrite/models/o_auth2_apple.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Apple(AppwriteModel): """ OAuth2Apple @@ -22,6 +23,7 @@ class OAuth2Apple(AppwriteModel): p8file : str Apple OAuth2 .p8 private key file contents. The secret key wrapped by the PEM markers is 200 characters long. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') serviceid: str = Field(..., alias='serviceId') diff --git a/appwrite/models/o_auth2_appwrite.py b/appwrite/models/o_auth2_appwrite.py index 002a8408..7d5f4a34 100644 --- a/appwrite/models/o_auth2_appwrite.py +++ b/appwrite/models/o_auth2_appwrite.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Appwrite(AppwriteModel): """ OAuth2Appwrite @@ -18,6 +19,7 @@ class OAuth2Appwrite(AppwriteModel): clientsecret : str Appwrite OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_auth0.py b/appwrite/models/o_auth2_auth0.py index 5c5b3ae2..d3d95e2f 100644 --- a/appwrite/models/o_auth2_auth0.py +++ b/appwrite/models/o_auth2_auth0.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Auth0(AppwriteModel): """ OAuth2Auth0 @@ -20,6 +21,7 @@ class OAuth2Auth0(AppwriteModel): endpoint : str Auth0 OAuth2 endpoint domain. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_authentik.py b/appwrite/models/o_auth2_authentik.py index b5d73c06..917c67eb 100644 --- a/appwrite/models/o_auth2_authentik.py +++ b/appwrite/models/o_auth2_authentik.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Authentik(AppwriteModel): """ OAuth2Authentik @@ -20,6 +21,7 @@ class OAuth2Authentik(AppwriteModel): endpoint : str Authentik OAuth2 endpoint domain. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_autodesk.py b/appwrite/models/o_auth2_autodesk.py index b5b879d8..69bf0aba 100644 --- a/appwrite/models/o_auth2_autodesk.py +++ b/appwrite/models/o_auth2_autodesk.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Autodesk(AppwriteModel): """ OAuth2Autodesk @@ -18,6 +19,7 @@ class OAuth2Autodesk(AppwriteModel): clientsecret : str Autodesk OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_bitbucket.py b/appwrite/models/o_auth2_bitbucket.py index d2028fba..a62d0979 100644 --- a/appwrite/models/o_auth2_bitbucket.py +++ b/appwrite/models/o_auth2_bitbucket.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Bitbucket(AppwriteModel): """ OAuth2Bitbucket @@ -18,6 +19,7 @@ class OAuth2Bitbucket(AppwriteModel): secret : str Bitbucket OAuth2 secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') key: str = Field(..., alias='key') diff --git a/appwrite/models/o_auth2_bitly.py b/appwrite/models/o_auth2_bitly.py index 39a250c3..f3284f4b 100644 --- a/appwrite/models/o_auth2_bitly.py +++ b/appwrite/models/o_auth2_bitly.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Bitly(AppwriteModel): """ OAuth2Bitly @@ -18,6 +19,7 @@ class OAuth2Bitly(AppwriteModel): clientsecret : str Bitly OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_box.py b/appwrite/models/o_auth2_box.py index 03538b4a..f64f0140 100644 --- a/appwrite/models/o_auth2_box.py +++ b/appwrite/models/o_auth2_box.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Box(AppwriteModel): """ OAuth2Box @@ -18,6 +19,7 @@ class OAuth2Box(AppwriteModel): clientsecret : str Box OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_dailymotion.py b/appwrite/models/o_auth2_dailymotion.py index a6ce3665..fa1836c3 100644 --- a/appwrite/models/o_auth2_dailymotion.py +++ b/appwrite/models/o_auth2_dailymotion.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Dailymotion(AppwriteModel): """ OAuth2Dailymotion @@ -18,6 +19,7 @@ class OAuth2Dailymotion(AppwriteModel): apisecret : str Dailymotion OAuth2 API secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') apikey: str = Field(..., alias='apiKey') diff --git a/appwrite/models/o_auth2_discord.py b/appwrite/models/o_auth2_discord.py index eb55fbca..8516e192 100644 --- a/appwrite/models/o_auth2_discord.py +++ b/appwrite/models/o_auth2_discord.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Discord(AppwriteModel): """ OAuth2Discord @@ -18,6 +19,7 @@ class OAuth2Discord(AppwriteModel): clientsecret : str Discord OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_disqus.py b/appwrite/models/o_auth2_disqus.py index 446e2e64..302fc486 100644 --- a/appwrite/models/o_auth2_disqus.py +++ b/appwrite/models/o_auth2_disqus.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Disqus(AppwriteModel): """ OAuth2Disqus @@ -18,6 +19,7 @@ class OAuth2Disqus(AppwriteModel): secretkey : str Disqus OAuth2 secret key. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') publickey: str = Field(..., alias='publicKey') diff --git a/appwrite/models/o_auth2_dropbox.py b/appwrite/models/o_auth2_dropbox.py index ff0b3368..d8b980f8 100644 --- a/appwrite/models/o_auth2_dropbox.py +++ b/appwrite/models/o_auth2_dropbox.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Dropbox(AppwriteModel): """ OAuth2Dropbox @@ -18,6 +19,7 @@ class OAuth2Dropbox(AppwriteModel): appsecret : str Dropbox OAuth2 app secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') appkey: str = Field(..., alias='appKey') diff --git a/appwrite/models/o_auth2_etsy.py b/appwrite/models/o_auth2_etsy.py index fb405633..9b3b7480 100644 --- a/appwrite/models/o_auth2_etsy.py +++ b/appwrite/models/o_auth2_etsy.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Etsy(AppwriteModel): """ OAuth2Etsy @@ -18,6 +19,7 @@ class OAuth2Etsy(AppwriteModel): sharedsecret : str Etsy OAuth2 shared secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') keystring: str = Field(..., alias='keyString') diff --git a/appwrite/models/o_auth2_facebook.py b/appwrite/models/o_auth2_facebook.py index c07100d1..83e72aa5 100644 --- a/appwrite/models/o_auth2_facebook.py +++ b/appwrite/models/o_auth2_facebook.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Facebook(AppwriteModel): """ OAuth2Facebook @@ -18,6 +19,7 @@ class OAuth2Facebook(AppwriteModel): appsecret : str Facebook OAuth2 app secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') appid: str = Field(..., alias='appId') diff --git a/appwrite/models/o_auth2_figma.py b/appwrite/models/o_auth2_figma.py index 8fa88a11..3ad1bb66 100644 --- a/appwrite/models/o_auth2_figma.py +++ b/appwrite/models/o_auth2_figma.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Figma(AppwriteModel): """ OAuth2Figma @@ -18,6 +19,7 @@ class OAuth2Figma(AppwriteModel): clientsecret : str Figma OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_fusion_auth.py b/appwrite/models/o_auth2_fusion_auth.py index d0c325d4..b38e63a3 100644 --- a/appwrite/models/o_auth2_fusion_auth.py +++ b/appwrite/models/o_auth2_fusion_auth.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2FusionAuth(AppwriteModel): """ OAuth2FusionAuth @@ -20,6 +21,7 @@ class OAuth2FusionAuth(AppwriteModel): endpoint : str FusionAuth OAuth2 endpoint domain. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_github.py b/appwrite/models/o_auth2_github.py index dd7ba070..d436fa70 100644 --- a/appwrite/models/o_auth2_github.py +++ b/appwrite/models/o_auth2_github.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Github(AppwriteModel): """ OAuth2GitHub @@ -18,6 +19,7 @@ class OAuth2Github(AppwriteModel): clientsecret : str GitHub OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_gitlab.py b/appwrite/models/o_auth2_gitlab.py index a1967792..3014d836 100644 --- a/appwrite/models/o_auth2_gitlab.py +++ b/appwrite/models/o_auth2_gitlab.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Gitlab(AppwriteModel): """ OAuth2Gitlab @@ -20,6 +21,7 @@ class OAuth2Gitlab(AppwriteModel): endpoint : str GitLab OAuth2 endpoint URL. Defaults to https://gitlab.com for self-hosted instances. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') applicationid: str = Field(..., alias='applicationId') diff --git a/appwrite/models/o_auth2_google.py b/appwrite/models/o_auth2_google.py index 8dcc33bd..7d815ef2 100644 --- a/appwrite/models/o_auth2_google.py +++ b/appwrite/models/o_auth2_google.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.o_auth2_google_prompt import OAuth2GooglePrompt + class OAuth2Google(AppwriteModel): """ OAuth2Google @@ -21,6 +22,7 @@ class OAuth2Google(AppwriteModel): prompt : List[OAuth2GooglePrompt] Google OAuth2 prompt values. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_hugging_face.py b/appwrite/models/o_auth2_hugging_face.py new file mode 100644 index 00000000..d35f9946 --- /dev/null +++ b/appwrite/models/o_auth2_hugging_face.py @@ -0,0 +1,26 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class OAuth2HuggingFace(AppwriteModel): + """ + OAuth2HuggingFace + + Attributes + ---------- + id : str + OAuth2 provider ID. + enabled : bool + OAuth2 provider is active and can be used to create sessions. + clientid : str + Hugging Face OAuth2 client ID. + clientsecret : str + Hugging Face OAuth2 client secret. + """ + + id: str = Field(..., alias='$id') + enabled: bool = Field(..., alias='enabled') + clientid: str = Field(..., alias='clientId') + clientsecret: str = Field(..., alias='clientSecret') diff --git a/appwrite/models/o_auth2_keycloak.py b/appwrite/models/o_auth2_keycloak.py index fb9f709c..674cfae4 100644 --- a/appwrite/models/o_auth2_keycloak.py +++ b/appwrite/models/o_auth2_keycloak.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Keycloak(AppwriteModel): """ OAuth2Keycloak @@ -22,6 +23,7 @@ class OAuth2Keycloak(AppwriteModel): realmname : str Keycloak OAuth2 realm name. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_kick.py b/appwrite/models/o_auth2_kick.py index 4e798a26..2ef797ed 100644 --- a/appwrite/models/o_auth2_kick.py +++ b/appwrite/models/o_auth2_kick.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Kick(AppwriteModel): """ OAuth2Kick @@ -18,6 +19,7 @@ class OAuth2Kick(AppwriteModel): clientsecret : str Kick OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_linkedin.py b/appwrite/models/o_auth2_linkedin.py index ed41f13e..62bc6d11 100644 --- a/appwrite/models/o_auth2_linkedin.py +++ b/appwrite/models/o_auth2_linkedin.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Linkedin(AppwriteModel): """ OAuth2Linkedin @@ -18,6 +19,7 @@ class OAuth2Linkedin(AppwriteModel): primaryclientsecret : str LinkedIn OAuth2 primary client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_microsoft.py b/appwrite/models/o_auth2_microsoft.py index 07ce5c64..50cbdd56 100644 --- a/appwrite/models/o_auth2_microsoft.py +++ b/appwrite/models/o_auth2_microsoft.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Microsoft(AppwriteModel): """ OAuth2Microsoft @@ -20,6 +21,7 @@ class OAuth2Microsoft(AppwriteModel): tenant : str Microsoft Entra ID tenant identifier. Use 'common', 'organizations', 'consumers' or a specific tenant ID. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') applicationid: str = Field(..., alias='applicationId') diff --git a/appwrite/models/o_auth2_notion.py b/appwrite/models/o_auth2_notion.py index 55a36d5f..8ce2bad2 100644 --- a/appwrite/models/o_auth2_notion.py +++ b/appwrite/models/o_auth2_notion.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Notion(AppwriteModel): """ OAuth2Notion @@ -18,6 +19,7 @@ class OAuth2Notion(AppwriteModel): oauthclientsecret : str Notion OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') oauthclientid: str = Field(..., alias='oauthClientId') diff --git a/appwrite/models/o_auth2_oidc.py b/appwrite/models/o_auth2_oidc.py index 0ad06fef..d2b65571 100644 --- a/appwrite/models/o_auth2_oidc.py +++ b/appwrite/models/o_auth2_oidc.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.o_auth2_oidc_prompt import OAuth2OidcPrompt + class OAuth2Oidc(AppwriteModel): """ OAuth2Oidc @@ -31,6 +32,7 @@ class OAuth2Oidc(AppwriteModel): maxage : Optional[float] Maximum authentication age in seconds. When set, the user must have authenticated within this many seconds. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_okta.py b/appwrite/models/o_auth2_okta.py index 192e56ea..4ecdd0b5 100644 --- a/appwrite/models/o_auth2_okta.py +++ b/appwrite/models/o_auth2_okta.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Okta(AppwriteModel): """ OAuth2Okta @@ -22,6 +23,7 @@ class OAuth2Okta(AppwriteModel): authorizationserverid : str Okta OAuth2 authorization server ID. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_paypal.py b/appwrite/models/o_auth2_paypal.py index 44b6f13e..a87cb0f8 100644 --- a/appwrite/models/o_auth2_paypal.py +++ b/appwrite/models/o_auth2_paypal.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Paypal(AppwriteModel): """ OAuth2Paypal @@ -18,6 +19,7 @@ class OAuth2Paypal(AppwriteModel): secretkey : str PayPal OAuth2 secret key. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_podio.py b/appwrite/models/o_auth2_podio.py index ff9d9bad..79b256c7 100644 --- a/appwrite/models/o_auth2_podio.py +++ b/appwrite/models/o_auth2_podio.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Podio(AppwriteModel): """ OAuth2Podio @@ -18,6 +19,7 @@ class OAuth2Podio(AppwriteModel): clientsecret : str Podio OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_provider_list.py b/appwrite/models/o_auth2_provider_list.py index e13f865a..64571e1e 100644 --- a/appwrite/models/o_auth2_provider_list.py +++ b/appwrite/models/o_auth2_provider_list.py @@ -43,6 +43,8 @@ from .o_auth2_okta import OAuth2Okta from .o_auth2_kick import OAuth2Kick from .o_auth2_microsoft import OAuth2Microsoft +from .o_auth2_hugging_face import OAuth2HuggingFace + class OAuth2ProviderList(AppwriteModel): """ @@ -52,8 +54,54 @@ class OAuth2ProviderList(AppwriteModel): ---------- total : float Total number of OAuth2 providers in the given project. - providers : List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Appwrite, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] + providers : List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Appwrite, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft, OAuth2HuggingFace]] List of OAuth2 providers. """ + total: float = Field(..., alias='total') - providers: List[Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Appwrite, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]] = Field(..., alias='providers') + providers: List[ + Union[ + OAuth2Github, + OAuth2Discord, + OAuth2Figma, + OAuth2Dropbox, + OAuth2Dailymotion, + OAuth2Bitbucket, + OAuth2Bitly, + OAuth2Box, + OAuth2Autodesk, + OAuth2Google, + OAuth2Zoom, + OAuth2Zoho, + OAuth2Yandex, + OAuth2X, + OAuth2WordPress, + OAuth2Twitch, + OAuth2Stripe, + OAuth2Spotify, + OAuth2Slack, + OAuth2Podio, + OAuth2Notion, + OAuth2Salesforce, + OAuth2Yahoo, + OAuth2Linkedin, + OAuth2Disqus, + OAuth2Amazon, + OAuth2Etsy, + OAuth2Facebook, + OAuth2Tradeshift, + OAuth2Paypal, + OAuth2Gitlab, + OAuth2Appwrite, + OAuth2Authentik, + OAuth2Auth0, + OAuth2FusionAuth, + OAuth2Keycloak, + OAuth2Oidc, + OAuth2Apple, + OAuth2Okta, + OAuth2Kick, + OAuth2Microsoft, + OAuth2HuggingFace, + ] + ] = Field(..., alias='providers') diff --git a/appwrite/models/o_auth2_salesforce.py b/appwrite/models/o_auth2_salesforce.py index a72f7dec..e1170360 100644 --- a/appwrite/models/o_auth2_salesforce.py +++ b/appwrite/models/o_auth2_salesforce.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Salesforce(AppwriteModel): """ OAuth2Salesforce @@ -18,6 +19,7 @@ class OAuth2Salesforce(AppwriteModel): customersecret : str Salesforce OAuth2 consumer secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') customerkey: str = Field(..., alias='customerKey') diff --git a/appwrite/models/o_auth2_slack.py b/appwrite/models/o_auth2_slack.py index 074934f0..220df0cc 100644 --- a/appwrite/models/o_auth2_slack.py +++ b/appwrite/models/o_auth2_slack.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Slack(AppwriteModel): """ OAuth2Slack @@ -18,6 +19,7 @@ class OAuth2Slack(AppwriteModel): clientsecret : str Slack OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_spotify.py b/appwrite/models/o_auth2_spotify.py index 90169546..e46d9355 100644 --- a/appwrite/models/o_auth2_spotify.py +++ b/appwrite/models/o_auth2_spotify.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Spotify(AppwriteModel): """ OAuth2Spotify @@ -18,6 +19,7 @@ class OAuth2Spotify(AppwriteModel): clientsecret : str Spotify OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_stripe.py b/appwrite/models/o_auth2_stripe.py index 47e3e696..c44a8727 100644 --- a/appwrite/models/o_auth2_stripe.py +++ b/appwrite/models/o_auth2_stripe.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Stripe(AppwriteModel): """ OAuth2Stripe @@ -18,6 +19,7 @@ class OAuth2Stripe(AppwriteModel): apisecretkey : str Stripe OAuth2 API secret key. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_tradeshift.py b/appwrite/models/o_auth2_tradeshift.py index 084424ed..284c2764 100644 --- a/appwrite/models/o_auth2_tradeshift.py +++ b/appwrite/models/o_auth2_tradeshift.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Tradeshift(AppwriteModel): """ OAuth2Tradeshift @@ -18,6 +19,7 @@ class OAuth2Tradeshift(AppwriteModel): oauth2clientsecret : str Tradeshift OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') oauth2clientid: str = Field(..., alias='oauth2ClientId') diff --git a/appwrite/models/o_auth2_twitch.py b/appwrite/models/o_auth2_twitch.py index 2df093f3..41b51d14 100644 --- a/appwrite/models/o_auth2_twitch.py +++ b/appwrite/models/o_auth2_twitch.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Twitch(AppwriteModel): """ OAuth2Twitch @@ -18,6 +19,7 @@ class OAuth2Twitch(AppwriteModel): clientsecret : str Twitch OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_word_press.py b/appwrite/models/o_auth2_word_press.py index 8c75dd23..64abedaf 100644 --- a/appwrite/models/o_auth2_word_press.py +++ b/appwrite/models/o_auth2_word_press.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2WordPress(AppwriteModel): """ OAuth2WordPress @@ -18,6 +19,7 @@ class OAuth2WordPress(AppwriteModel): clientsecret : str WordPress OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_x.py b/appwrite/models/o_auth2_x.py index 1cd5ea8d..8dfeb6d3 100644 --- a/appwrite/models/o_auth2_x.py +++ b/appwrite/models/o_auth2_x.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2X(AppwriteModel): """ OAuth2X @@ -18,6 +19,7 @@ class OAuth2X(AppwriteModel): secretkey : str X OAuth2 secret key. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') customerkey: str = Field(..., alias='customerKey') diff --git a/appwrite/models/o_auth2_yahoo.py b/appwrite/models/o_auth2_yahoo.py index fbf734ca..f1c4a518 100644 --- a/appwrite/models/o_auth2_yahoo.py +++ b/appwrite/models/o_auth2_yahoo.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Yahoo(AppwriteModel): """ OAuth2Yahoo @@ -18,6 +19,7 @@ class OAuth2Yahoo(AppwriteModel): clientsecret : str Yahoo OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_yandex.py b/appwrite/models/o_auth2_yandex.py index 3945f62c..c0c93f1a 100644 --- a/appwrite/models/o_auth2_yandex.py +++ b/appwrite/models/o_auth2_yandex.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Yandex(AppwriteModel): """ OAuth2Yandex @@ -18,6 +19,7 @@ class OAuth2Yandex(AppwriteModel): clientsecret : str Yandex OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_zoho.py b/appwrite/models/o_auth2_zoho.py index 2e9119b5..249420f2 100644 --- a/appwrite/models/o_auth2_zoho.py +++ b/appwrite/models/o_auth2_zoho.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Zoho(AppwriteModel): """ OAuth2Zoho @@ -18,6 +19,7 @@ class OAuth2Zoho(AppwriteModel): clientsecret : str Zoho OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/o_auth2_zoom.py b/appwrite/models/o_auth2_zoom.py index 00f66594..4770761e 100644 --- a/appwrite/models/o_auth2_zoom.py +++ b/appwrite/models/o_auth2_zoom.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class OAuth2Zoom(AppwriteModel): """ OAuth2Zoom @@ -18,6 +19,7 @@ class OAuth2Zoom(AppwriteModel): clientsecret : str Zoom OAuth2 client secret. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') clientid: str = Field(..., alias='clientId') diff --git a/appwrite/models/oauth2_approve.py b/appwrite/models/oauth2_approve.py index 4e7d6fab..48b41a9f 100644 --- a/appwrite/models/oauth2_approve.py +++ b/appwrite/models/oauth2_approve.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Approve(AppwriteModel): """ OAuth2 Approve @@ -12,4 +13,5 @@ class Oauth2Approve(AppwriteModel): redirecturl : str URL the end user should be redirected to after the grant is approved, carrying the authorization `code` and/or `id_token` along with the original `state`. """ + redirecturl: str = Field(..., alias='redirectUrl') diff --git a/appwrite/models/oauth2_authorize.py b/appwrite/models/oauth2_authorize.py index 8afb4749..34c09c30 100644 --- a/appwrite/models/oauth2_authorize.py +++ b/appwrite/models/oauth2_authorize.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Authorize(AppwriteModel): """ OAuth2 Authorize @@ -14,5 +15,6 @@ class Oauth2Authorize(AppwriteModel): redirecturl : str URL the end user should be redirected to when the flow can complete without consent. Empty when consent is still required. """ + grantid: str = Field(..., alias='grantId') redirecturl: str = Field(..., alias='redirectUrl') diff --git a/appwrite/models/oauth2_consent.py b/appwrite/models/oauth2_consent.py index 6675856b..22b5805a 100644 --- a/appwrite/models/oauth2_consent.py +++ b/appwrite/models/oauth2_consent.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Consent(AppwriteModel): """ OAuth2 Consent @@ -30,6 +31,7 @@ class Oauth2Consent(AppwriteModel): expire : str Consent expiration time in ISO 8601 format. Empty when the consent has no token-bound expiry yet. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/oauth2_consent_list.py b/appwrite/models/oauth2_consent_list.py index 610353b6..cf1ded74 100644 --- a/appwrite/models/oauth2_consent_list.py +++ b/appwrite/models/oauth2_consent_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .oauth2_consent import Oauth2Consent + class Oauth2ConsentList(AppwriteModel): """ OAuth2 consents list @@ -15,5 +16,6 @@ class Oauth2ConsentList(AppwriteModel): consents : List[Oauth2Consent] List of consents. """ + total: float = Field(..., alias='total') consents: List[Oauth2Consent] = Field(..., alias='consents') diff --git a/appwrite/models/oauth2_consent_token.py b/appwrite/models/oauth2_consent_token.py index 2fd26ca5..022d826d 100644 --- a/appwrite/models/oauth2_consent_token.py +++ b/appwrite/models/oauth2_consent_token.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2ConsentToken(AppwriteModel): """ OAuth2 Consent Token @@ -32,6 +33,7 @@ class Oauth2ConsentToken(AppwriteModel): expire : str Expiration time of the current access token of this family in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/oauth2_consent_token_list.py b/appwrite/models/oauth2_consent_token_list.py index e4864cdb..d64c366d 100644 --- a/appwrite/models/oauth2_consent_token_list.py +++ b/appwrite/models/oauth2_consent_token_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .oauth2_consent_token import Oauth2ConsentToken + class Oauth2ConsentTokenList(AppwriteModel): """ OAuth2 consent tokens list @@ -15,5 +16,6 @@ class Oauth2ConsentTokenList(AppwriteModel): tokens : List[Oauth2ConsentToken] List of tokens. """ + total: float = Field(..., alias='total') tokens: List[Oauth2ConsentToken] = Field(..., alias='tokens') diff --git a/appwrite/models/oauth2_device_authorization.py b/appwrite/models/oauth2_device_authorization.py index 66413a71..4d423857 100644 --- a/appwrite/models/oauth2_device_authorization.py +++ b/appwrite/models/oauth2_device_authorization.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2DeviceAuthorization(AppwriteModel): """ OAuth2 Device Authorization @@ -22,6 +23,7 @@ class Oauth2DeviceAuthorization(AppwriteModel): interval : float Minimum polling interval for the token endpoint in seconds. """ + device_code: str = Field(..., alias='device_code') user_code: str = Field(..., alias='user_code') verification_uri: str = Field(..., alias='verification_uri') diff --git a/appwrite/models/oauth2_grant.py b/appwrite/models/oauth2_grant.py index 58676082..ffa000d9 100644 --- a/appwrite/models/oauth2_grant.py +++ b/appwrite/models/oauth2_grant.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Grant(AppwriteModel): """ OAuth2 Grant @@ -34,6 +35,7 @@ class Oauth2Grant(AppwriteModel): expire : str Grant expiration time in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/oauth2_organization.py b/appwrite/models/oauth2_organization.py index 4481c4b2..4df5b972 100644 --- a/appwrite/models/oauth2_organization.py +++ b/appwrite/models/oauth2_organization.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Organization(AppwriteModel): """ OAuth2 Organization @@ -12,4 +13,5 @@ class Oauth2Organization(AppwriteModel): id : str Organization ID. """ + id: str = Field(..., alias='$id') diff --git a/appwrite/models/oauth2_organization_list.py b/appwrite/models/oauth2_organization_list.py index aee823a0..b1dbba39 100644 --- a/appwrite/models/oauth2_organization_list.py +++ b/appwrite/models/oauth2_organization_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .oauth2_organization import Oauth2Organization + class Oauth2OrganizationList(AppwriteModel): """ OAuth2 accessible organizations list @@ -15,5 +16,6 @@ class Oauth2OrganizationList(AppwriteModel): organizations : List[Oauth2Organization] List of organizations. """ + total: float = Field(..., alias='total') organizations: List[Oauth2Organization] = Field(..., alias='organizations') diff --git a/appwrite/models/oauth2_par.py b/appwrite/models/oauth2_par.py index a5942c86..49d8b20b 100644 --- a/appwrite/models/oauth2_par.py +++ b/appwrite/models/oauth2_par.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2PAR(AppwriteModel): """ OAuth2 PAR @@ -14,5 +15,6 @@ class Oauth2PAR(AppwriteModel): expires_in : float Lifetime of the authorization request handle in seconds. """ + request_uri: str = Field(..., alias='request_uri') expires_in: float = Field(..., alias='expires_in') diff --git a/appwrite/models/oauth2_project.py b/appwrite/models/oauth2_project.py index f7bac058..0c06806a 100644 --- a/appwrite/models/oauth2_project.py +++ b/appwrite/models/oauth2_project.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Project(AppwriteModel): """ OAuth2 Project @@ -16,6 +17,7 @@ class Oauth2Project(AppwriteModel): endpoint : str API endpoint of the region the project is deployed in. Empty when the region has no public hostname configured. """ + id: str = Field(..., alias='$id') region: str = Field(..., alias='region') endpoint: str = Field(..., alias='endpoint') diff --git a/appwrite/models/oauth2_project_list.py b/appwrite/models/oauth2_project_list.py index e67b8929..03864e13 100644 --- a/appwrite/models/oauth2_project_list.py +++ b/appwrite/models/oauth2_project_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .oauth2_project import Oauth2Project + class Oauth2ProjectList(AppwriteModel): """ OAuth2 accessible projects list @@ -15,5 +16,6 @@ class Oauth2ProjectList(AppwriteModel): projects : List[Oauth2Project] List of projects. """ + total: float = Field(..., alias='total') projects: List[Oauth2Project] = Field(..., alias='projects') diff --git a/appwrite/models/oauth2_reject.py b/appwrite/models/oauth2_reject.py index b76c5073..148df6df 100644 --- a/appwrite/models/oauth2_reject.py +++ b/appwrite/models/oauth2_reject.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Reject(AppwriteModel): """ OAuth2 Reject @@ -12,4 +13,5 @@ class Oauth2Reject(AppwriteModel): redirecturl : str URL the end user should be redirected to after the grant is rejected, carrying an `access_denied` error. """ + redirecturl: str = Field(..., alias='redirectUrl') diff --git a/appwrite/models/oauth2_token.py b/appwrite/models/oauth2_token.py index 83d6dc99..81f7e851 100644 --- a/appwrite/models/oauth2_token.py +++ b/appwrite/models/oauth2_token.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Oauth2Token(AppwriteModel): """ OAuth2 Token @@ -24,6 +25,7 @@ class Oauth2Token(AppwriteModel): id_token : Optional[str] OpenID Connect ID token. Returned when the `openid` scope is granted. """ + access_token: str = Field(..., alias='access_token') token_type: str = Field(..., alias='token_type') expires_in: float = Field(..., alias='expires_in') diff --git a/appwrite/models/organization.py b/appwrite/models/organization.py index 604be7d5..cb1a59b6 100644 --- a/appwrite/models/organization.py +++ b/appwrite/models/organization.py @@ -8,6 +8,7 @@ T = TypeVar('T') + class Organization(AppwriteModel, Generic[T]): """ Organization @@ -85,6 +86,7 @@ class Organization(AppwriteModel, Generic[T]): projects : List[Any] Selected projects """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -126,7 +128,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Organiz """Create Organization instance with typed data.""" instance = cls.model_validate(data) if 'prefs' in data and data['prefs'] is not None: - instance.prefs = Preferences.with_data( - data['prefs'], model_type - ) + instance.prefs = Preferences.with_data(data['prefs'], model_type) return instance diff --git a/appwrite/models/phone.py b/appwrite/models/phone.py index 8242ee10..9df4f3e2 100644 --- a/appwrite/models/phone.py +++ b/appwrite/models/phone.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Phone(AppwriteModel): """ Phone @@ -16,6 +17,7 @@ class Phone(AppwriteModel): countryname : str Country name. """ + code: str = Field(..., alias='code') countrycode: str = Field(..., alias='countryCode') countryname: str = Field(..., alias='countryName') diff --git a/appwrite/models/phone_list.py b/appwrite/models/phone_list.py index b84cde18..e9cc2679 100644 --- a/appwrite/models/phone_list.py +++ b/appwrite/models/phone_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .phone import Phone + class PhoneList(AppwriteModel): """ Phones List @@ -15,5 +16,6 @@ class PhoneList(AppwriteModel): phones : List[Phone] List of phones. """ + total: float = Field(..., alias='total') phones: List[Phone] = Field(..., alias='phones') diff --git a/appwrite/models/platform_android.py b/appwrite/models/platform_android.py index 3ec35873..ade36f3f 100644 --- a/appwrite/models/platform_android.py +++ b/appwrite/models/platform_android.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.platform_type import PlatformType + class PlatformAndroid(AppwriteModel): """ Platform Android @@ -23,6 +24,7 @@ class PlatformAndroid(AppwriteModel): applicationid : str Android application ID. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/platform_apple.py b/appwrite/models/platform_apple.py index 3e94d780..1d1cb315 100644 --- a/appwrite/models/platform_apple.py +++ b/appwrite/models/platform_apple.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.platform_type import PlatformType + class PlatformApple(AppwriteModel): """ Platform Apple @@ -23,6 +24,7 @@ class PlatformApple(AppwriteModel): bundleidentifier : str Apple bundle identifier. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/platform_linux.py b/appwrite/models/platform_linux.py index ead049a5..82958e80 100644 --- a/appwrite/models/platform_linux.py +++ b/appwrite/models/platform_linux.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.platform_type import PlatformType + class PlatformLinux(AppwriteModel): """ Platform Linux @@ -23,6 +24,7 @@ class PlatformLinux(AppwriteModel): packagename : str Linux package name. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/platform_list.py b/appwrite/models/platform_list.py index 07cca317..eb30c63f 100644 --- a/appwrite/models/platform_list.py +++ b/appwrite/models/platform_list.py @@ -8,6 +8,7 @@ from .platform_windows import PlatformWindows from .platform_linux import PlatformLinux + class PlatformList(AppwriteModel): """ Platforms List @@ -19,5 +20,14 @@ class PlatformList(AppwriteModel): platforms : List[Union[PlatformWeb, PlatformApple, PlatformAndroid, PlatformWindows, PlatformLinux]] List of platforms. """ + total: float = Field(..., alias='total') - platforms: List[Union[PlatformWeb, PlatformApple, PlatformAndroid, PlatformWindows, PlatformLinux]] = Field(..., alias='platforms') + platforms: List[ + Union[ + PlatformWeb, + PlatformApple, + PlatformAndroid, + PlatformWindows, + PlatformLinux, + ] + ] = Field(..., alias='platforms') diff --git a/appwrite/models/platform_web.py b/appwrite/models/platform_web.py index 7b143be3..4e69b96f 100644 --- a/appwrite/models/platform_web.py +++ b/appwrite/models/platform_web.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.platform_type import PlatformType + class PlatformWeb(AppwriteModel): """ Platform Web @@ -23,6 +24,7 @@ class PlatformWeb(AppwriteModel): hostname : str Web app hostname. Empty string for other platforms. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/platform_windows.py b/appwrite/models/platform_windows.py index 78b2e0ae..fdabffb2 100644 --- a/appwrite/models/platform_windows.py +++ b/appwrite/models/platform_windows.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.platform_type import PlatformType + class PlatformWindows(AppwriteModel): """ Platform Windows @@ -23,6 +24,7 @@ class PlatformWindows(AppwriteModel): packageidentifiername : str Windows package identifier name. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/policy_deny_aliased_email.py b/appwrite/models/policy_deny_aliased_email.py index 765fab82..64e65644 100644 --- a/appwrite/models/policy_deny_aliased_email.py +++ b/appwrite/models/policy_deny_aliased_email.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyDenyAliasedEmail(AppwriteModel): """ Policy Deny Aliased Email @@ -14,5 +15,6 @@ class PolicyDenyAliasedEmail(AppwriteModel): enabled : bool Whether the deny aliased email policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_deny_corporate_email.py b/appwrite/models/policy_deny_corporate_email.py index af00e330..b56e12fb 100644 --- a/appwrite/models/policy_deny_corporate_email.py +++ b/appwrite/models/policy_deny_corporate_email.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyDenyCorporateEmail(AppwriteModel): """ Policy Deny Corporate Email @@ -14,5 +15,6 @@ class PolicyDenyCorporateEmail(AppwriteModel): enabled : bool Whether the deny non-corporate email policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_deny_disposable_email.py b/appwrite/models/policy_deny_disposable_email.py index 458018c0..4f571733 100644 --- a/appwrite/models/policy_deny_disposable_email.py +++ b/appwrite/models/policy_deny_disposable_email.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyDenyDisposableEmail(AppwriteModel): """ Policy Deny Disposable Email @@ -14,5 +15,6 @@ class PolicyDenyDisposableEmail(AppwriteModel): enabled : bool Whether the deny disposable email policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_deny_free_email.py b/appwrite/models/policy_deny_free_email.py index 6e1672a7..1eb610ee 100644 --- a/appwrite/models/policy_deny_free_email.py +++ b/appwrite/models/policy_deny_free_email.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyDenyFreeEmail(AppwriteModel): """ Policy Deny Free Email @@ -14,5 +15,6 @@ class PolicyDenyFreeEmail(AppwriteModel): enabled : bool Whether the deny free email policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_list.py b/appwrite/models/policy_list.py index f00999b3..79e8802c 100644 --- a/appwrite/models/policy_list.py +++ b/appwrite/models/policy_list.py @@ -18,6 +18,7 @@ from .policy_deny_free_email import PolicyDenyFreeEmail from .policy_deny_corporate_email import PolicyDenyCorporateEmail + class PolicyList(AppwriteModel): """ Policies List @@ -29,5 +30,24 @@ class PolicyList(AppwriteModel): policies : List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] List of policies. """ + total: float = Field(..., alias='total') - policies: List[Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]] = Field(..., alias='policies') + policies: List[ + Union[ + PolicyPasswordDictionary, + PolicyPasswordHistory, + PolicyPasswordStrength, + PolicyPasswordPersonalData, + PolicySessionAlert, + PolicySessionDuration, + PolicySessionInvalidation, + PolicySessionLimit, + PolicyUserLimit, + PolicyMembershipPrivacy, + PolicyMfaFactors, + PolicyDenyAliasedEmail, + PolicyDenyDisposableEmail, + PolicyDenyFreeEmail, + PolicyDenyCorporateEmail, + ] + ] = Field(..., alias='policies') diff --git a/appwrite/models/policy_membership_privacy.py b/appwrite/models/policy_membership_privacy.py index e3e2a5bc..157913ac 100644 --- a/appwrite/models/policy_membership_privacy.py +++ b/appwrite/models/policy_membership_privacy.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyMembershipPrivacy(AppwriteModel): """ Policy Membership Privacy @@ -24,6 +25,7 @@ class PolicyMembershipPrivacy(AppwriteModel): useraccessedat : bool Whether user last access time is visible in memberships. """ + id: str = Field(..., alias='$id') userid: bool = Field(..., alias='userId') useremail: bool = Field(..., alias='userEmail') diff --git a/appwrite/models/policy_mfa_factors.py b/appwrite/models/policy_mfa_factors.py index 8ff59740..12b5b20b 100644 --- a/appwrite/models/policy_mfa_factors.py +++ b/appwrite/models/policy_mfa_factors.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyMfaFactors(AppwriteModel): """ Policy MFA Factors @@ -20,6 +21,7 @@ class PolicyMfaFactors(AppwriteModel): custom : bool Whether the custom factor can be used to complete an MFA challenge. """ + id: str = Field(..., alias='$id') totp: bool = Field(..., alias='totp') email: bool = Field(..., alias='email') diff --git a/appwrite/models/policy_password_dictionary.py b/appwrite/models/policy_password_dictionary.py index 8a544cfd..e5046106 100644 --- a/appwrite/models/policy_password_dictionary.py +++ b/appwrite/models/policy_password_dictionary.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyPasswordDictionary(AppwriteModel): """ Policy Password Dictionary @@ -14,5 +15,6 @@ class PolicyPasswordDictionary(AppwriteModel): enabled : bool Whether password dictionary policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_password_history.py b/appwrite/models/policy_password_history.py index 76e0f182..f8eff9a7 100644 --- a/appwrite/models/policy_password_history.py +++ b/appwrite/models/policy_password_history.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyPasswordHistory(AppwriteModel): """ Policy Password History @@ -14,5 +15,6 @@ class PolicyPasswordHistory(AppwriteModel): total : float Password history length. A value of 0 means the policy is disabled. """ + id: str = Field(..., alias='$id') total: float = Field(..., alias='total') diff --git a/appwrite/models/policy_password_personal_data.py b/appwrite/models/policy_password_personal_data.py index f3c6ee6c..92710579 100644 --- a/appwrite/models/policy_password_personal_data.py +++ b/appwrite/models/policy_password_personal_data.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyPasswordPersonalData(AppwriteModel): """ Policy Password Personal Data @@ -14,5 +15,6 @@ class PolicyPasswordPersonalData(AppwriteModel): enabled : bool Whether password personal data policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_password_strength.py b/appwrite/models/policy_password_strength.py index 7abb100a..db9b6bc6 100644 --- a/appwrite/models/policy_password_strength.py +++ b/appwrite/models/policy_password_strength.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyPasswordStrength(AppwriteModel): """ Policy Password Strength @@ -22,6 +23,7 @@ class PolicyPasswordStrength(AppwriteModel): symbols : bool Whether passwords must include at least one symbol. """ + id: str = Field(..., alias='$id') min: float = Field(..., alias='min') uppercase: bool = Field(..., alias='uppercase') diff --git a/appwrite/models/policy_session_alert.py b/appwrite/models/policy_session_alert.py index 368b8ed5..f8f87a4d 100644 --- a/appwrite/models/policy_session_alert.py +++ b/appwrite/models/policy_session_alert.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicySessionAlert(AppwriteModel): """ Policy Session Alert @@ -14,5 +15,6 @@ class PolicySessionAlert(AppwriteModel): enabled : bool Whether session alert policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_session_duration.py b/appwrite/models/policy_session_duration.py index cc1adc0c..7b688476 100644 --- a/appwrite/models/policy_session_duration.py +++ b/appwrite/models/policy_session_duration.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicySessionDuration(AppwriteModel): """ Policy Session Duration @@ -14,5 +15,6 @@ class PolicySessionDuration(AppwriteModel): duration : float Session duration in seconds. """ + id: str = Field(..., alias='$id') duration: float = Field(..., alias='duration') diff --git a/appwrite/models/policy_session_invalidation.py b/appwrite/models/policy_session_invalidation.py index 0b5251bf..ffce62db 100644 --- a/appwrite/models/policy_session_invalidation.py +++ b/appwrite/models/policy_session_invalidation.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicySessionInvalidation(AppwriteModel): """ Policy Session Invalidation @@ -14,5 +15,6 @@ class PolicySessionInvalidation(AppwriteModel): enabled : bool Whether session invalidation policy is enabled. """ + id: str = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/policy_session_limit.py b/appwrite/models/policy_session_limit.py index b1d4b77b..36590466 100644 --- a/appwrite/models/policy_session_limit.py +++ b/appwrite/models/policy_session_limit.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicySessionLimit(AppwriteModel): """ Policy Session Limit @@ -14,5 +15,6 @@ class PolicySessionLimit(AppwriteModel): total : float Maximum number of sessions allowed per user. A value of 0 means the policy is disabled. """ + id: str = Field(..., alias='$id') total: float = Field(..., alias='total') diff --git a/appwrite/models/policy_user_limit.py b/appwrite/models/policy_user_limit.py index 3a6df697..485879fd 100644 --- a/appwrite/models/policy_user_limit.py +++ b/appwrite/models/policy_user_limit.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class PolicyUserLimit(AppwriteModel): """ Policy User Limit @@ -14,5 +15,6 @@ class PolicyUserLimit(AppwriteModel): total : float Maximum number of users allowed in the project. A value of 0 means the policy is disabled. """ + id: str = Field(..., alias='$id') total: float = Field(..., alias='total') diff --git a/appwrite/models/postgres_extension.py b/appwrite/models/postgres_extension.py new file mode 100644 index 00000000..9f8cfdc7 --- /dev/null +++ b/appwrite/models/postgres_extension.py @@ -0,0 +1,26 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel + + +class PostgresExtension(AppwriteModel): + """ + Postgres extension + + Attributes + ---------- + key : str + Extension key used with CREATE EXTENSION. + name : str + Human-readable extension name. + description : str + Short description of what the extension provides. + category : str + Category the extension belongs to. + """ + + key: str = Field(..., alias='key') + name: str = Field(..., alias='name') + description: str = Field(..., alias='description') + category: str = Field(..., alias='category') diff --git a/appwrite/models/preferences.py b/appwrite/models/preferences.py index 5d655bd1..2811f37a 100644 --- a/appwrite/models/preferences.py +++ b/appwrite/models/preferences.py @@ -7,10 +7,12 @@ _PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Preferences(AppwriteModel, Generic[T]): """ Preferences """ + pass @classmethod diff --git a/appwrite/models/presence.py b/appwrite/models/presence.py index d4afedb1..79556f7a 100644 --- a/appwrite/models/presence.py +++ b/appwrite/models/presence.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Presence(AppwriteModel): """ Presence @@ -28,6 +29,7 @@ class Presence(AppwriteModel): metadata : Optional[Dict[str, Any]] Presence metadata. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/presence_list.py b/appwrite/models/presence_list.py index 2d37c0e4..1d8752a6 100644 --- a/appwrite/models/presence_list.py +++ b/appwrite/models/presence_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .presence import Presence + class PresenceList(AppwriteModel): """ Presences List @@ -15,5 +16,6 @@ class PresenceList(AppwriteModel): presences : List[Presence] List of presences. """ + total: float = Field(..., alias='total') presences: List[Presence] = Field(..., alias='presences') diff --git a/appwrite/models/program.py b/appwrite/models/program.py index 49f068e9..e2f5b081 100644 --- a/appwrite/models/program.py +++ b/appwrite/models/program.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Program(AppwriteModel): """ Program @@ -28,6 +29,7 @@ class Program(AppwriteModel): billingplanid : str Billing plan ID that this is program is associated with. """ + id: str = Field(..., alias='$id') title: str = Field(..., alias='title') description: str = Field(..., alias='description') diff --git a/appwrite/models/project.py b/appwrite/models/project.py index bc9abb12..08721a9b 100644 --- a/appwrite/models/project.py +++ b/appwrite/models/project.py @@ -9,6 +9,7 @@ from .block import Block from .billing_limits import BillingLimits + class Project(AppwriteModel): """ Project @@ -69,7 +70,7 @@ class Project(AppwriteModel): Project blocks information consoleaccessedat : str Last time the project was accessed via console. Used with plan's projectInactivityDays to determine if project is paused. - wafenabled : bool + wafenabled : Optional[bool] Whether WAF enforcement is enabled for the project. billinglimits : Optional[BillingLimits] Billing limits reached @@ -108,6 +109,7 @@ class Project(AppwriteModel): oauth2serverdiscoveryurl : Optional[str] OAuth2 server discovery URL """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -135,19 +137,31 @@ class Project(AppwriteModel): protocols: List[ProjectProtocol] = Field(..., alias='protocols') blocks: List[Block] = Field(..., alias='blocks') consoleaccessedat: str = Field(..., alias='consoleAccessedAt') - wafenabled: bool = Field(..., alias='wafEnabled') + wafenabled: Optional[bool] = Field(default=None, alias='wafEnabled') billinglimits: Optional[BillingLimits] = Field(default=None, alias='billingLimits') oauth2serverenabled: Optional[bool] = Field(default=None, alias='oAuth2ServerEnabled') oauth2serverauthorizationurl: Optional[str] = Field(default=None, alias='oAuth2ServerAuthorizationUrl') oauth2serverscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerScopes') oauth2serverdefaultscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerDefaultScopes') oauth2serverinstallationscopes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerInstallationScopes') - oauth2serverauthorizationdetailstypes: Optional[List[Any]] = Field(default=None, alias='oAuth2ServerAuthorizationDetailsTypes') + oauth2serverauthorizationdetailstypes: Optional[List[Any]] = Field( + default=None, + alias='oAuth2ServerAuthorizationDetailsTypes', + ) oauth2serveraccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerAccessTokenDuration') oauth2serverrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerRefreshTokenDuration') - oauth2serverpublicaccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerPublicAccessTokenDuration') - oauth2serverpublicrefreshtokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerPublicRefreshTokenDuration') - oauth2serverinstallationaccesstokenduration: Optional[float] = Field(default=None, alias='oAuth2ServerInstallationAccessTokenDuration') + oauth2serverpublicaccesstokenduration: Optional[float] = Field( + default=None, + alias='oAuth2ServerPublicAccessTokenDuration', + ) + oauth2serverpublicrefreshtokenduration: Optional[float] = Field( + default=None, + alias='oAuth2ServerPublicRefreshTokenDuration', + ) + oauth2serverinstallationaccesstokenduration: Optional[float] = Field( + default=None, + alias='oAuth2ServerInstallationAccessTokenDuration', + ) oauth2serverconfidentialpkce: Optional[bool] = Field(default=None, alias='oAuth2ServerConfidentialPkce') oauth2serververificationurl: Optional[str] = Field(default=None, alias='oAuth2ServerVerificationUrl') oauth2serverusercodelength: Optional[float] = Field(default=None, alias='oAuth2ServerUserCodeLength') diff --git a/appwrite/models/project_auth_method.py b/appwrite/models/project_auth_method.py index 92db259c..76df540b 100644 --- a/appwrite/models/project_auth_method.py +++ b/appwrite/models/project_auth_method.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.project_auth_method_id import ProjectAuthMethodId + class ProjectAuthMethod(AppwriteModel): """ ProjectAuthMethod @@ -15,5 +16,6 @@ class ProjectAuthMethod(AppwriteModel): enabled : bool Auth method status. """ + id: ProjectAuthMethodId = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/project_list.py b/appwrite/models/project_list.py index c41de6f6..31cc5425 100644 --- a/appwrite/models/project_list.py +++ b/appwrite/models/project_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .project import Project + class ProjectList(AppwriteModel): """ Projects List @@ -15,5 +16,6 @@ class ProjectList(AppwriteModel): projects : List[Project] List of projects. """ + total: float = Field(..., alias='total') projects: List[Project] = Field(..., alias='projects') diff --git a/appwrite/models/project_protocol.py b/appwrite/models/project_protocol.py index be2374fb..8be9c7e7 100644 --- a/appwrite/models/project_protocol.py +++ b/appwrite/models/project_protocol.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.project_protocol_id import ProjectProtocolId + class ProjectProtocol(AppwriteModel): """ ProjectProtocol @@ -15,5 +16,6 @@ class ProjectProtocol(AppwriteModel): enabled : bool Protocol status. """ + id: ProjectProtocolId = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/project_service.py b/appwrite/models/project_service.py index 99e0ed88..da1d0df4 100644 --- a/appwrite/models/project_service.py +++ b/appwrite/models/project_service.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from ..enums.project_service_id import ProjectServiceId + class ProjectService(AppwriteModel): """ ProjectService @@ -15,5 +16,6 @@ class ProjectService(AppwriteModel): enabled : bool Service status. """ + id: ProjectServiceId = Field(..., alias='$id') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/provider.py b/appwrite/models/provider.py index 88a28b84..b08954cd 100644 --- a/appwrite/models/provider.py +++ b/appwrite/models/provider.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Provider(AppwriteModel): """ Provider @@ -28,6 +29,7 @@ class Provider(AppwriteModel): options : Optional[Dict[str, Any]] Provider options. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/provider_list.py b/appwrite/models/provider_list.py index 9f476dc9..c6265653 100644 --- a/appwrite/models/provider_list.py +++ b/appwrite/models/provider_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .provider import Provider + class ProviderList(AppwriteModel): """ Provider list @@ -15,5 +16,6 @@ class ProviderList(AppwriteModel): providers : List[Provider] List of providers. """ + total: float = Field(..., alias='total') providers: List[Provider] = Field(..., alias='providers') diff --git a/appwrite/models/proxy_invalidation.py b/appwrite/models/proxy_invalidation.py index 511a0feb..586ba9e3 100644 --- a/appwrite/models/proxy_invalidation.py +++ b/appwrite/models/proxy_invalidation.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class ProxyInvalidation(AppwriteModel): """ Invalidation @@ -18,6 +19,7 @@ class ProxyInvalidation(AppwriteModel): status : str Invalidation status. """ + domain: str = Field(..., alias='domain') type: str = Field(..., alias='type') reference: str = Field(..., alias='reference') diff --git a/appwrite/models/proxy_rule.py b/appwrite/models/proxy_rule.py index 2154f849..53a3d0d8 100644 --- a/appwrite/models/proxy_rule.py +++ b/appwrite/models/proxy_rule.py @@ -5,6 +5,7 @@ from ..enums.proxy_rule_deployment_resource_type import ProxyRuleDeploymentResourceType from ..enums.proxy_rule_status import ProxyRuleStatus + class ProxyRule(AppwriteModel): """ Rule @@ -42,6 +43,7 @@ class ProxyRule(AppwriteModel): renewat : str Certificate auto-renewal date in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -51,7 +53,10 @@ class ProxyRule(AppwriteModel): redirecturl: str = Field(..., alias='redirectUrl') redirectstatuscode: float = Field(..., alias='redirectStatusCode') deploymentid: str = Field(..., alias='deploymentId') - deploymentresourcetype: Optional[ProxyRuleDeploymentResourceType] = Field(default=None, alias='deploymentResourceType') + deploymentresourcetype: Optional[ProxyRuleDeploymentResourceType] = Field( + default=None, + alias='deploymentResourceType', + ) deploymentresourceid: str = Field(..., alias='deploymentResourceId') deploymentvcsproviderbranch: str = Field(..., alias='deploymentVcsProviderBranch') status: ProxyRuleStatus = Field(..., alias='status') diff --git a/appwrite/models/proxy_rule_list.py b/appwrite/models/proxy_rule_list.py index ce500c2a..8c266224 100644 --- a/appwrite/models/proxy_rule_list.py +++ b/appwrite/models/proxy_rule_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .proxy_rule import ProxyRule + class ProxyRuleList(AppwriteModel): """ Rule List @@ -15,5 +16,6 @@ class ProxyRuleList(AppwriteModel): rules : List[ProxyRule] List of rules. """ + total: float = Field(..., alias='total') rules: List[ProxyRule] = Field(..., alias='rules') diff --git a/appwrite/models/report.py b/appwrite/models/report.py index fe10e4e8..88241b4f 100644 --- a/appwrite/models/report.py +++ b/appwrite/models/report.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .insight import Insight + class Report(AppwriteModel): """ Report @@ -35,6 +36,7 @@ class Report(AppwriteModel): analyzedat : Optional[str] Time the report was analyzed in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/report_list.py b/appwrite/models/report_list.py index 05fe12f9..3edfb434 100644 --- a/appwrite/models/report_list.py +++ b/appwrite/models/report_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .report import Report + class ReportList(AppwriteModel): """ Reports List @@ -15,5 +16,6 @@ class ReportList(AppwriteModel): reports : List[Report] List of reports. """ + total: float = Field(..., alias='total') reports: List[Report] = Field(..., alias='reports') diff --git a/appwrite/models/resource_token.py b/appwrite/models/resource_token.py index 35eff96a..c8b9ec05 100644 --- a/appwrite/models/resource_token.py +++ b/appwrite/models/resource_token.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class ResourceToken(AppwriteModel): """ ResourceToken @@ -24,6 +25,7 @@ class ResourceToken(AppwriteModel): accessedat : str Most recent access date in ISO 8601 format. This attribute is only updated again after 24 hours. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') resourceid: str = Field(..., alias='resourceId') diff --git a/appwrite/models/resource_token_list.py b/appwrite/models/resource_token_list.py index 422ebc40..b1ee177e 100644 --- a/appwrite/models/resource_token_list.py +++ b/appwrite/models/resource_token_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .resource_token import ResourceToken + class ResourceTokenList(AppwriteModel): """ Resource Tokens List @@ -15,5 +16,6 @@ class ResourceTokenList(AppwriteModel): tokens : List[ResourceToken] List of tokens. """ + total: float = Field(..., alias='total') tokens: List[ResourceToken] = Field(..., alias='tokens') diff --git a/appwrite/models/row.py b/appwrite/models/row.py index f421cd17..5a8aa39e 100644 --- a/appwrite/models/row.py +++ b/appwrite/models/row.py @@ -7,6 +7,7 @@ _PAYLOAD_ADAPTER = TypeAdapter(Dict[str, Any]) + class Row(AppwriteModel, Generic[T]): """ Row @@ -28,6 +29,7 @@ class Row(AppwriteModel, Generic[T]): permissions : List[Any] Row permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). """ + id: str = Field(..., alias='$id') sequence: str = Field(..., alias='$sequence') tableid: str = Field(..., alias='$tableId') @@ -39,7 +41,15 @@ class Row(AppwriteModel, Generic[T]): @classmethod def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Row[T]': """Create Row instance with typed data.""" - internal_aliases = {'$id', '$sequence', '$tableId', '$databaseId', '$createdAt', '$updatedAt', '$permissions'} + internal_aliases = { + '$id', + '$sequence', + '$tableId', + '$databaseId', + '$createdAt', + '$updatedAt', + '$permissions', + } internal_fields = {k: v for k, v in data.items() if k in internal_aliases} user_data = {k: v for k, v in data.items() if k not in internal_aliases and k != 'data'} nested = data.get('data') diff --git a/appwrite/models/row_list.py b/appwrite/models/row_list.py index b4508b2a..174b973d 100644 --- a/appwrite/models/row_list.py +++ b/appwrite/models/row_list.py @@ -6,6 +6,7 @@ T = TypeVar('T') + class RowList(AppwriteModel, Generic[T]): """ Rows List @@ -17,6 +18,7 @@ class RowList(AppwriteModel, Generic[T]): rows : List[Row[T]] List of rows. """ + total: float = Field(..., alias='total') rows: List[Row[T]] = Field(..., alias='rows') @@ -25,8 +27,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'RowList """Create RowList instance with typed data.""" instance = cls.model_validate(data) if 'rows' in data and data['rows'] is not None: - instance.rows = [ - Row.with_data(row, model_type) - for row in data['rows'] - ] + instance.rows = [Row.with_data(row, model_type) for row in data['rows']] return instance diff --git a/appwrite/models/runtime.py b/appwrite/models/runtime.py index f42ea12c..debc5e8a 100644 --- a/appwrite/models/runtime.py +++ b/appwrite/models/runtime.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Runtime(AppwriteModel): """ Runtime @@ -26,6 +27,7 @@ class Runtime(AppwriteModel): supports : List[Any] List of supported architectures. """ + id: str = Field(..., alias='$id') key: str = Field(..., alias='key') name: str = Field(..., alias='name') diff --git a/appwrite/models/runtime_list.py b/appwrite/models/runtime_list.py index 34d03348..18121a93 100644 --- a/appwrite/models/runtime_list.py +++ b/appwrite/models/runtime_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .runtime import Runtime + class RuntimeList(AppwriteModel): """ Runtimes List @@ -15,5 +16,6 @@ class RuntimeList(AppwriteModel): runtimes : List[Runtime] List of runtimes. """ + total: float = Field(..., alias='total') runtimes: List[Runtime] = Field(..., alias='runtimes') diff --git a/appwrite/models/session.py b/appwrite/models/session.py index 8487c1c3..01f10bfa 100644 --- a/appwrite/models/session.py +++ b/appwrite/models/session.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Session(AppwriteModel): """ Session @@ -68,6 +69,7 @@ class Session(AppwriteModel): mfaupdatedat : str Most recent date in ISO 8601 format when the session successfully passed MFA challenge. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/session_list.py b/appwrite/models/session_list.py index 6b37cb56..7518f56a 100644 --- a/appwrite/models/session_list.py +++ b/appwrite/models/session_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .session import Session + class SessionList(AppwriteModel): """ Sessions List @@ -15,5 +16,6 @@ class SessionList(AppwriteModel): sessions : List[Session] List of sessions. """ + total: float = Field(..., alias='total') sessions: List[Session] = Field(..., alias='sessions') diff --git a/appwrite/models/site.py b/appwrite/models/site.py index a4ecfef9..b6f2aad6 100644 --- a/appwrite/models/site.py +++ b/appwrite/models/site.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .variable import Variable + class Site(AppwriteModel): """ Site @@ -42,6 +43,8 @@ class Site(AppwriteModel): Latest deployment creation date in ISO 8601 format. latestdeploymentstatus : str Status of latest deployment. Possible values are "waiting", "processing", "building", "ready", and "failed". + scopes : List[Any] + Allowed permission scopes. vars : List[Variable] Site variables. timeout : float @@ -79,6 +82,7 @@ class Site(AppwriteModel): fallbackfile : str Name of fallback file to use instead of 404 page. If null, Appwrite 404 page will be displayed. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -95,6 +99,7 @@ class Site(AppwriteModel): latestdeploymentid: str = Field(..., alias='latestDeploymentId') latestdeploymentcreatedat: str = Field(..., alias='latestDeploymentCreatedAt') latestdeploymentstatus: str = Field(..., alias='latestDeploymentStatus') + scopes: List[Any] = Field(..., alias='scopes') vars: List[Variable] = Field(..., alias='vars') timeout: float = Field(..., alias='timeout') installcommand: str = Field(..., alias='installCommand') diff --git a/appwrite/models/site_list.py b/appwrite/models/site_list.py index 87eb6729..cd60234d 100644 --- a/appwrite/models/site_list.py +++ b/appwrite/models/site_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .site import Site + class SiteList(AppwriteModel): """ Sites List @@ -15,5 +16,6 @@ class SiteList(AppwriteModel): sites : List[Site] List of sites. """ + total: float = Field(..., alias='total') sites: List[Site] = Field(..., alias='sites') diff --git a/appwrite/models/specification.py b/appwrite/models/specification.py index 832cfb80..6f65491f 100644 --- a/appwrite/models/specification.py +++ b/appwrite/models/specification.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Specification(AppwriteModel): """ Specification @@ -18,6 +19,7 @@ class Specification(AppwriteModel): slug : str Size slug. """ + memory: float = Field(..., alias='memory') cpus: float = Field(..., alias='cpus') enabled: bool = Field(..., alias='enabled') diff --git a/appwrite/models/specification_list.py b/appwrite/models/specification_list.py index d302f943..e05ad6db 100644 --- a/appwrite/models/specification_list.py +++ b/appwrite/models/specification_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .specification import Specification + class SpecificationList(AppwriteModel): """ Specifications List @@ -15,5 +16,6 @@ class SpecificationList(AppwriteModel): specifications : List[Specification] List of specifications. """ + total: float = Field(..., alias='total') specifications: List[Specification] = Field(..., alias='specifications') diff --git a/appwrite/models/subscriber.py b/appwrite/models/subscriber.py index a0a6c1de..80d8e390 100644 --- a/appwrite/models/subscriber.py +++ b/appwrite/models/subscriber.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .target import Target + class Subscriber(AppwriteModel): """ Subscriber @@ -29,6 +30,7 @@ class Subscriber(AppwriteModel): providertype : str The target provider type. Can be one of the following: `email`, `sms` or `push`. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/subscriber_list.py b/appwrite/models/subscriber_list.py index 35bf8438..cb346700 100644 --- a/appwrite/models/subscriber_list.py +++ b/appwrite/models/subscriber_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .subscriber import Subscriber + class SubscriberList(AppwriteModel): """ Subscriber list @@ -15,5 +16,6 @@ class SubscriberList(AppwriteModel): subscribers : List[Subscriber] List of subscribers. """ + total: float = Field(..., alias='total') subscribers: List[Subscriber] = Field(..., alias='subscribers') diff --git a/appwrite/models/table.py b/appwrite/models/table.py index de5f21e0..6e4a5cbf 100644 --- a/appwrite/models/table.py +++ b/appwrite/models/table.py @@ -22,6 +22,7 @@ from .column_string import ColumnString from .column_index import ColumnIndex + class Table(AppwriteModel): """ Table @@ -53,6 +54,7 @@ class Table(AppwriteModel): bytesused : float Currently used row size in bytes based on defined columns. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -61,7 +63,28 @@ class Table(AppwriteModel): name: str = Field(..., alias='name') enabled: bool = Field(..., alias='enabled') rowsecurity: bool = Field(..., alias='rowSecurity') - columns: List[Union[ColumnBoolean, ColumnBigint, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnPoint, ColumnLine, ColumnPolygon, ColumnVarchar, ColumnText, ColumnMediumtext, ColumnLongtext, ColumnString]] = Field(..., alias='columns') + columns: List[ + Union[ + ColumnBoolean, + ColumnBigint, + ColumnInteger, + ColumnFloat, + ColumnEmail, + ColumnEnum, + ColumnUrl, + ColumnIp, + ColumnDatetime, + ColumnRelationship, + ColumnPoint, + ColumnLine, + ColumnPolygon, + ColumnVarchar, + ColumnText, + ColumnMediumtext, + ColumnLongtext, + ColumnString, + ] + ] = Field(..., alias='columns') indexes: List[ColumnIndex] = Field(..., alias='indexes') bytesmax: float = Field(..., alias='bytesMax') bytesused: float = Field(..., alias='bytesUsed') diff --git a/appwrite/models/table_list.py b/appwrite/models/table_list.py index f617c918..9d8b29f2 100644 --- a/appwrite/models/table_list.py +++ b/appwrite/models/table_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .table import Table + class TableList(AppwriteModel): """ Tables List @@ -15,5 +16,6 @@ class TableList(AppwriteModel): tables : List[Table] List of tables. """ + total: float = Field(..., alias='total') tables: List[Table] = Field(..., alias='tables') diff --git a/appwrite/models/target.py b/appwrite/models/target.py index d68a52de..de38e227 100644 --- a/appwrite/models/target.py +++ b/appwrite/models/target.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Target(AppwriteModel): """ Target @@ -28,6 +29,7 @@ class Target(AppwriteModel): expired : bool Is the target expired. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/target_list.py b/appwrite/models/target_list.py index dd99f7a1..095aa9bf 100644 --- a/appwrite/models/target_list.py +++ b/appwrite/models/target_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .target import Target + class TargetList(AppwriteModel): """ Target list @@ -15,5 +16,6 @@ class TargetList(AppwriteModel): targets : List[Target] List of targets. """ + total: float = Field(..., alias='total') targets: List[Target] = Field(..., alias='targets') diff --git a/appwrite/models/team.py b/appwrite/models/team.py index 9298951c..c1f13ab4 100644 --- a/appwrite/models/team.py +++ b/appwrite/models/team.py @@ -6,6 +6,7 @@ T = TypeVar('T') + class Team(AppwriteModel, Generic[T]): """ Team @@ -25,6 +26,7 @@ class Team(AppwriteModel, Generic[T]): prefs : Preferences[T] Team preferences as a key-value object """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') @@ -37,7 +39,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'Team[T] """Create Team instance with typed data.""" instance = cls.model_validate(data) if 'prefs' in data and data['prefs'] is not None: - instance.prefs = Preferences.with_data( - data['prefs'], model_type - ) + instance.prefs = Preferences.with_data(data['prefs'], model_type) return instance diff --git a/appwrite/models/team_list.py b/appwrite/models/team_list.py index 85610b5c..682e09d7 100644 --- a/appwrite/models/team_list.py +++ b/appwrite/models/team_list.py @@ -6,6 +6,7 @@ T = TypeVar('T') + class TeamList(AppwriteModel, Generic[T]): """ Teams List @@ -17,6 +18,7 @@ class TeamList(AppwriteModel, Generic[T]): teams : List[Team[T]] List of teams. """ + total: float = Field(..., alias='total') teams: List[Team[T]] = Field(..., alias='teams') @@ -25,8 +27,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'TeamLis """Create TeamList instance with typed data.""" instance = cls.model_validate(data) if 'teams' in data and data['teams'] is not None: - instance.teams = [ - Team.with_data(row, model_type) - for row in data['teams'] - ] + instance.teams = [Team.with_data(row, model_type) for row in data['teams']] return instance diff --git a/appwrite/models/token.py b/appwrite/models/token.py index 5bc7588a..b99233d2 100644 --- a/appwrite/models/token.py +++ b/appwrite/models/token.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Token(AppwriteModel): """ Token @@ -22,6 +23,7 @@ class Token(AppwriteModel): phrase : str Security phrase of a token. Empty if security phrase was not requested when creating a token. It includes randomly generated phrase which is also sent in the external resource such as email. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') userid: str = Field(..., alias='userId') diff --git a/appwrite/models/topic.py b/appwrite/models/topic.py index 04dad6c8..ee1005b1 100644 --- a/appwrite/models/topic.py +++ b/appwrite/models/topic.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Topic(AppwriteModel): """ Topic @@ -26,6 +27,7 @@ class Topic(AppwriteModel): subscribe : List[Any] Subscribe permissions. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/topic_list.py b/appwrite/models/topic_list.py index a217a8c1..e739ccb5 100644 --- a/appwrite/models/topic_list.py +++ b/appwrite/models/topic_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .topic import Topic + class TopicList(AppwriteModel): """ Topic list @@ -15,5 +16,6 @@ class TopicList(AppwriteModel): topics : List[Topic] List of topics. """ + total: float = Field(..., alias='total') topics: List[Topic] = Field(..., alias='topics') diff --git a/appwrite/models/transaction.py b/appwrite/models/transaction.py index e1dd7af9..03461ab3 100644 --- a/appwrite/models/transaction.py +++ b/appwrite/models/transaction.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Transaction(AppwriteModel): """ Transaction @@ -22,6 +23,7 @@ class Transaction(AppwriteModel): expiresat : str Expiration time in ISO 8601 format. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/transaction_list.py b/appwrite/models/transaction_list.py index b85aaec9..a6c7184d 100644 --- a/appwrite/models/transaction_list.py +++ b/appwrite/models/transaction_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .transaction import Transaction + class TransactionList(AppwriteModel): """ Transaction List @@ -15,5 +16,6 @@ class TransactionList(AppwriteModel): transactions : List[Transaction] List of transactions. """ + total: float = Field(..., alias='total') transactions: List[Transaction] = Field(..., alias='transactions') diff --git a/appwrite/models/usage_billing_plan.py b/appwrite/models/usage_billing_plan.py index 40016c29..1951161a 100644 --- a/appwrite/models/usage_billing_plan.py +++ b/appwrite/models/usage_billing_plan.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .additional_resource import AdditionalResource + class UsageBillingPlan(AppwriteModel): """ usageBillingPlan @@ -33,6 +34,7 @@ class UsageBillingPlan(AppwriteModel): credits : Optional[AdditionalResource] Credits additional resources """ + bandwidth: AdditionalResource = Field(..., alias='bandwidth') executions: AdditionalResource = Field(..., alias='executions') member: Optional[AdditionalResource] = Field(default=None, alias='member') diff --git a/appwrite/models/user.py b/appwrite/models/user.py index 034c0052..c3891c04 100644 --- a/appwrite/models/user.py +++ b/appwrite/models/user.py @@ -14,6 +14,7 @@ T = TypeVar('T') + class User(AppwriteModel, Generic[T]): """ User @@ -73,13 +74,24 @@ class User(AppwriteModel, Generic[T]): impersonatoruserid : Optional[str] ID of the original actor performing the impersonation. Present only when the current request is impersonating another user. Internal audit logs attribute the action to this user, while the impersonated target is recorded only in internal audit payload data. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') name: str = Field(..., alias='name') password: Optional[str] = Field(default=None, alias='password') hash: Optional[str] = Field(default=None, alias='hash') - hashoptions: Optional[Union[AlgoArgon2, AlgoScrypt, AlgoScryptModified, AlgoBcrypt, AlgoPhpass, AlgoSha, AlgoMd5]] = Field(default=None, alias='hashOptions') + hashoptions: Optional[ + Union[ + AlgoArgon2, + AlgoScrypt, + AlgoScryptModified, + AlgoBcrypt, + AlgoPhpass, + AlgoSha, + AlgoMd5, + ] + ] = Field(default=None, alias='hashOptions') registration: str = Field(..., alias='registration') status: bool = Field(..., alias='status') labels: List[Any] = Field(..., alias='labels') @@ -105,7 +117,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'User[T] """Create User instance with typed data.""" instance = cls.model_validate(data) if 'prefs' in data and data['prefs'] is not None: - instance.prefs = Preferences.with_data( - data['prefs'], model_type - ) + instance.prefs = Preferences.with_data(data['prefs'], model_type) return instance diff --git a/appwrite/models/user_list.py b/appwrite/models/user_list.py index fa071b9c..7c6c7a2d 100644 --- a/appwrite/models/user_list.py +++ b/appwrite/models/user_list.py @@ -6,6 +6,7 @@ T = TypeVar('T') + class UserList(AppwriteModel, Generic[T]): """ Users List @@ -17,6 +18,7 @@ class UserList(AppwriteModel, Generic[T]): users : List[User[T]] List of users. """ + total: float = Field(..., alias='total') users: List[User[T]] = Field(..., alias='users') @@ -25,8 +27,5 @@ def with_data(cls, data: Dict[str, Any], model_type: Type[T] = dict) -> 'UserLis """Create UserList instance with typed data.""" instance = cls.model_validate(data) if 'users' in data and data['users'] is not None: - instance.users = [ - User.with_data(row, model_type) - for row in data['users'] - ] + instance.users = [User.with_data(row, model_type) for row in data['users']] return instance diff --git a/appwrite/models/variable.py b/appwrite/models/variable.py index 2988077e..c89b1cbc 100644 --- a/appwrite/models/variable.py +++ b/appwrite/models/variable.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Variable(AppwriteModel): """ Variable @@ -26,6 +27,7 @@ class Variable(AppwriteModel): resourceid : str ID of resource to which the variable belongs. If resourceType is "project", it is empty. If resourceType is "function", it is ID of the function. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/variable_list.py b/appwrite/models/variable_list.py index bb140a26..9307112e 100644 --- a/appwrite/models/variable_list.py +++ b/appwrite/models/variable_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .variable import Variable + class VariableList(AppwriteModel): """ Variables List @@ -15,5 +16,6 @@ class VariableList(AppwriteModel): variables : List[Variable] List of variables. """ + total: float = Field(..., alias='total') variables: List[Variable] = Field(..., alias='variables') diff --git a/appwrite/models/vectorsdb_collection.py b/appwrite/models/vectorsdb_collection.py new file mode 100644 index 00000000..bfdae1d9 --- /dev/null +++ b/appwrite/models/vectorsdb_collection.py @@ -0,0 +1,61 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .attribute_object import AttributeObject +from .attribute_vector import AttributeVector +from .index import Index + + +class VectorsdbCollection(AppwriteModel): + """ + VectorsDB Collection + + Attributes + ---------- + id : str + Collection ID. + createdat : str + Collection creation date in ISO 8601 format. + updatedat : str + Collection update date in ISO 8601 format. + permissions : List[Any] + Collection permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + databaseid : str + Database ID. + name : str + Collection name. + enabled : bool + Collection enabled. Can be 'enabled' or 'disabled'. When disabled, the collection is inaccessible to users, but remains accessible to Server SDKs using API keys. + documentsecurity : bool + Whether document-level permissions are enabled. [Learn more about permissions](https://appwrite.io/docs/permissions). + attributes : List[Union[AttributeObject, AttributeVector]] + Collection attributes. + indexes : List[Index] + Collection indexes. + bytesmax : float + Maximum document size in bytes. Returns 0 when no limit applies. + bytesused : float + Currently used document size in bytes based on defined attributes. + dimension : float + Embedding dimension. + """ + + id: str = Field(..., alias='$id') + createdat: str = Field(..., alias='$createdAt') + updatedat: str = Field(..., alias='$updatedAt') + permissions: List[Any] = Field(..., alias='$permissions') + databaseid: str = Field(..., alias='databaseId') + name: str = Field(..., alias='name') + enabled: bool = Field(..., alias='enabled') + documentsecurity: bool = Field(..., alias='documentSecurity') + attributes: List[ + Union[ + AttributeObject, + AttributeVector, + ] + ] = Field(..., alias='attributes') + indexes: List[Index] = Field(..., alias='indexes') + bytesmax: float = Field(..., alias='bytesMax') + bytesused: float = Field(..., alias='bytesUsed') + dimension: float = Field(..., alias='dimension') diff --git a/appwrite/models/vectorsdb_collection_list.py b/appwrite/models/vectorsdb_collection_list.py new file mode 100644 index 00000000..2e930e8d --- /dev/null +++ b/appwrite/models/vectorsdb_collection_list.py @@ -0,0 +1,21 @@ +from typing import Any, Dict, List, Optional, Union, cast +from pydantic import Field, PrivateAttr + +from .base_model import AppwriteModel +from .vectorsdb_collection import VectorsdbCollection + + +class VectorsdbCollectionList(AppwriteModel): + """ + VectorsDB Collections List + + Attributes + ---------- + total : float + Total number of collections that matched your query. + collections : List[VectorsdbCollection] + List of collections. + """ + + total: float = Field(..., alias='total') + collections: List[VectorsdbCollection] = Field(..., alias='collections') diff --git a/appwrite/models/webhook.py b/appwrite/models/webhook.py index 01beb3b3..ede2e0ad 100644 --- a/appwrite/models/webhook.py +++ b/appwrite/models/webhook.py @@ -3,6 +3,7 @@ from .base_model import AppwriteModel + class Webhook(AppwriteModel): """ Webhook @@ -36,6 +37,7 @@ class Webhook(AppwriteModel): attempts : float Number of consecutive failed webhook attempts. """ + id: str = Field(..., alias='$id') createdat: str = Field(..., alias='$createdAt') updatedat: str = Field(..., alias='$updatedAt') diff --git a/appwrite/models/webhook_list.py b/appwrite/models/webhook_list.py index fca455a8..537ea090 100644 --- a/appwrite/models/webhook_list.py +++ b/appwrite/models/webhook_list.py @@ -4,6 +4,7 @@ from .base_model import AppwriteModel from .webhook import Webhook + class WebhookList(AppwriteModel): """ Webhooks List @@ -15,5 +16,6 @@ class WebhookList(AppwriteModel): webhooks : List[Webhook] List of webhooks. """ + total: float = Field(..., alias='total') webhooks: List[Webhook] = Field(..., alias='webhooks') diff --git a/appwrite/operator.py b/appwrite/operator.py index ddec91ec..40b5b3fd 100644 --- a/appwrite/operator.py +++ b/appwrite/operator.py @@ -2,6 +2,7 @@ import math from enum import Enum + class Condition(Enum): EQUAL = "equal" NOT_EQUAL = "notEqual" @@ -13,7 +14,8 @@ class Condition(Enum): IS_NULL = "isNull" IS_NOT_NULL = "isNotNull" -class Operator(): + +class Operator: def __init__(self, method, values=None): self.method = method @@ -21,11 +23,7 @@ def __init__(self, method, values=None): self.values = values if isinstance(values, list) else [values] def __str__(self): - return json.dumps( - self.__dict__, - separators=(",", ":"), - default=lambda obj: obj.__dict__ - ) + return json.dumps(self.__dict__, separators=(",", ":"), default=lambda obj: obj.__dict__) @staticmethod def increment(value=1, max=None): diff --git a/appwrite/query.py b/appwrite/query.py index 3dafd4aa..154a19e6 100644 --- a/appwrite/query.py +++ b/appwrite/query.py @@ -1,7 +1,8 @@ import json + # Inherit from dict to allow for easy serialization -class Query(): +class Query: def __init__(self, method, attribute=None, values=None): self.method = method @@ -12,11 +13,7 @@ def __init__(self, method, attribute=None, values=None): self.values = values if isinstance(values, list) else [values] def __str__(self): - return json.dumps( - self.__dict__, - separators=(",", ":"), - default=lambda obj: obj.__dict__ - ) + return json.dumps(self.__dict__, separators=(",", ":"), default=lambda obj: obj.__dict__) @staticmethod def equal(attribute, value): diff --git a/appwrite/role.py b/appwrite/role.py index 8506fe1e..a6cb29d7 100644 --- a/appwrite/role.py +++ b/appwrite/role.py @@ -1,15 +1,16 @@ class Role: """Helper class to generate role strings for `Permission`.""" + @staticmethod def any(): """Grants access to anyone. - + This includes authenticated and unauthenticated users. """ return 'any' @staticmethod - def user(id, status = ""): + def user(id, status=""): """Grants access to a specific user by user ID. You can optionally pass verified or unverified for @@ -29,9 +30,9 @@ def user(id, status = ""): return f'user:{id}' @staticmethod - def users(status = ""): + def users(status=""): """Grants access to any authenticated or anonymous user. - + You can optionally pass verified or unverified for `status` to target specific types of users. @@ -46,7 +47,7 @@ def users(status = ""): if status: return f'users/{status}' return 'users' - + @staticmethod def guests(): """Grants access to any guest user without a session. @@ -60,7 +61,7 @@ def guests(): return 'guests' @staticmethod - def team(id, role = ""): + def team(id, role=""): """Grants access to a team by team ID. You can optionally pass a role for `role` to target @@ -108,4 +109,4 @@ def label(name): ------- str """ - return f'label:{name}' \ No newline at end of file + return f'label:{name}' diff --git a/appwrite/service.py b/appwrite/service.py index fef16a05..abc7cf4b 100644 --- a/appwrite/service.py +++ b/appwrite/service.py @@ -9,6 +9,7 @@ ModelType = TypeVar('ModelType', bound=AppwriteModel) + class Service: def __init__(self, client: Client): self.client = client @@ -24,18 +25,11 @@ def _normalize_value(self, value: Any) -> Any: return [self._normalize_value(item) for item in value] if isinstance(value, dict): - return { - key: self._normalize_value(item) - for key, item in value.items() - } + return {key: self._normalize_value(item) for key, item in value.items()} return value - def _parse_response( - self, - response: Any, - model: Optional[Type[ModelType]] = None - ) -> Any: + def _parse_response(self, response: Any, model: Optional[Type[ModelType]] = None) -> Any: if model is None: return response diff --git a/appwrite/services/__init__.py b/appwrite/services/__init__.py index 0519ecba..e69de29b 100644 --- a/appwrite/services/__init__.py +++ b/appwrite/services/__init__.py @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/appwrite/services/account.py b/appwrite/services/account.py index ee1f0f96..286f1ee5 100644 --- a/appwrite/services/account.py +++ b/appwrite/services/account.py @@ -24,6 +24,7 @@ T = TypeVar('T') + class Account(Service): def __init__(self, client) -> None: @@ -31,22 +32,21 @@ def __init__(self, client) -> None: def get( self, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Get the currently logged in user. Parameters ---------- - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -56,21 +56,25 @@ def get( api_path = '/account' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create( self, user_id: str, email: str, password: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Use this endpoint to allow a new user to register a new account in your project. After the user registration completes successfully, you can use the [/account/verfication](https://appwrite.io/docs/references/cloud/client-web/account#createVerification) route to start verifying the user email address. To allow the new user to login to their new account, you need to create a new [account session](https://appwrite.io/docs/references/cloud/client-web/account#createEmailSession). @@ -85,15 +89,14 @@ def create( New user password. Must be between 8 and 256 chars. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -104,33 +107,33 @@ def create( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def list_consents( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> Oauth2ConsentList: """ Get a list of the OAuth2 consents the current user has given to third-party apps. @@ -141,12 +144,11 @@ def list_consents( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- Oauth2ConsentList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -155,23 +157,26 @@ def list_consents( api_path = '/account/consents' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2ConsentList) - def get_consent( self, - consent_id: str + consent_id: str, ) -> Oauth2Consent: """ Get an OAuth2 consent the current user has given to a third-party app by its unique ID. @@ -180,12 +185,11 @@ def get_consent( ---------- consent_id : str Consent unique ID. - Returns ------- Oauth2Consent API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -196,21 +200,23 @@ def get_consent( api_params = {} if consent_id is None: raise AppwriteException('Missing required parameter: "consent_id"') - api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Consent) - def delete_consent( self, - consent_id: str + consent_id: str, ) -> Dict[str, Any]: """ Delete an OAuth2 consent by its unique ID. All token families issued under the consent are revoked, and the app must ask for consent again to regain access. @@ -219,12 +225,11 @@ def delete_consent( ---------- consent_id : str Consent unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -235,24 +240,26 @@ def delete_consent( api_params = {} if consent_id is None: raise AppwriteException('Missing required parameter: "consent_id"') - api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_consent_tokens( self, consent_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> Oauth2ConsentTokenList: """ Get a list of the token families issued under an OAuth2 consent. Each entry represents one authorized device or session; the token secrets themselves are never returned. @@ -265,12 +272,11 @@ def list_consent_tokens( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- Oauth2ConsentTokenList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -281,26 +287,28 @@ def list_consent_tokens( api_params = {} if consent_id is None: raise AppwriteException('Missing required parameter: "consent_id"') - api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2ConsentTokenList) - def get_consent_token( self, consent_id: str, - token_id: str + token_id: str, ) -> Oauth2ConsentToken: """ Get a token family issued under an OAuth2 consent by its unique ID. The token secrets themselves are never returned. @@ -311,12 +319,11 @@ def get_consent_token( Consent unique ID. token_id : str Token unique ID. - Returns ------- Oauth2ConsentToken API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -327,26 +334,27 @@ def get_consent_token( api_params = {} if consent_id is None: raise AppwriteException('Missing required parameter: "consent_id"') - if token_id is None: raise AppwriteException('Missing required parameter: "token_id"') - api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2ConsentToken) - def delete_consent_token( self, consent_id: str, - token_id: str + token_id: str, ) -> Dict[str, Any]: """ Delete a token family issued under an OAuth2 consent by its unique ID. The access and refresh tokens of the family stop working immediately; other token families and the consent itself are unaffected. @@ -357,12 +365,11 @@ def delete_consent_token( Consent unique ID. token_id : str Token unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -373,33 +380,33 @@ def delete_consent_token( api_params = {} if consent_id is None: raise AppwriteException('Missing required parameter: "consent_id"') - if token_id is None: raise AppwriteException('Missing required parameter: "token_id"') - api_path = api_path.replace('{consentId}', str(self._normalize_value(consent_id))) api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def update_email( self, email: str, password: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update currently logged in user account email address. After changing user address, the user confirmation status will get reset. A new confirmation email is not sent automatically however you can use the send confirmation email endpoint again to send the confirmation email. For security measures, user password is required to complete this request. This endpoint can also be used to convert an anonymous account to a normal one, by passing an email address and a new password. - Parameters ---------- @@ -407,15 +414,14 @@ def update_email( User email. password : str User password. Must be at least 8 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -426,27 +432,28 @@ def update_email( api_params = {} if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def list_identities( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> IdentityList: """ Get the list of identities for the currently logged in user. @@ -457,12 +464,11 @@ def list_identities( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: userId, provider, providerUid, providerEmail, providerAccessTokenExpiry total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- IdentityList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -471,23 +477,26 @@ def list_identities( api_path = '/account/identities' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=IdentityList) - def delete_identity( self, - identity_id: str + identity_id: str, ) -> Dict[str, Any]: """ Delete an identity by its unique ID. @@ -496,12 +505,11 @@ def delete_identity( ---------- identity_id : str Identity ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -512,22 +520,24 @@ def delete_identity( api_params = {} if identity_id is None: raise AppwriteException('Missing required parameter: "identity_id"') - api_path = api_path.replace('{identityId}', str(self._normalize_value(identity_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_logs( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> LogList: """ Get the list of latest security activity logs for the currently logged in user. Each log returns user IP address, location and date and time of log. @@ -538,12 +548,11 @@ def list_logs( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- LogList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -552,24 +561,27 @@ def list_logs( api_path = '/account/logs' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=LogList) - def update_mfa( self, mfa: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Enable or disable MFA on an account. @@ -578,15 +590,14 @@ def update_mfa( ---------- mfa : bool Enable or disable MFA. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -597,22 +608,24 @@ def update_mfa( api_params = {} if mfa is None: raise AppwriteException('Missing required parameter: "mfa"') - - api_params['mfa'] = self._normalize_value(mfa) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_mfa_authenticator( self, - type: AuthenticatorType + type: AuthenticatorType, ) -> MfaType: """ Add an authenticator app to be used as an MFA factor. Verify the authenticator using the [verify authenticator](/docs/references/cloud/client-web/account#updateMfaAuthenticator) method. @@ -621,12 +634,11 @@ def create_mfa_authenticator( ---------- type : AuthenticatorType Type of authenticator. Must be `totp` - Returns ------- MfaType API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -637,24 +649,26 @@ def create_mfa_authenticator( api_params = {} if type is None: raise AppwriteException('Missing required parameter: "type"') - api_path = api_path.replace('{type}', str(self._normalize_value(type))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaType) - def update_mfa_authenticator( self, type: AuthenticatorType, otp: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Verify an authenticator app after adding it using the [add authenticator](/docs/references/cloud/client-web/account#createMfaAuthenticator) method. @@ -665,15 +679,14 @@ def update_mfa_authenticator( Type of authenticator. otp : str Valid verification token. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -684,26 +697,27 @@ def update_mfa_authenticator( api_params = {} if type is None: raise AppwriteException('Missing required parameter: "type"') - if otp is None: raise AppwriteException('Missing required parameter: "otp"') - api_path = api_path.replace('{type}', str(self._normalize_value(type))) - api_params['otp'] = self._normalize_value(otp) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def delete_mfa_authenticator( self, - type: AuthenticatorType + type: AuthenticatorType, ) -> Dict[str, Any]: """ Delete an authenticator for a user by ID. @@ -712,12 +726,11 @@ def delete_mfa_authenticator( ---------- type : AuthenticatorType Type of authenticator. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -728,21 +741,23 @@ def delete_mfa_authenticator( api_params = {} if type is None: raise AppwriteException('Missing required parameter: "type"') - api_path = api_path.replace('{type}', str(self._normalize_value(type))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_mfa_challenge( self, - factor: AuthenticationFactor + factor: AuthenticationFactor, ) -> MfaChallenge: """ Begin the process of MFA verification after sign-in. Finish the flow with [updateMfaChallenge](/docs/references/cloud/client-web/account#updateMfaChallenge) method. @@ -751,12 +766,11 @@ def create_mfa_challenge( ---------- factor : AuthenticationFactor Factor used for verification. Must be one of following: `email`, `phone`, `totp`, `recoveryCode`, `custom`. - Returns ------- MfaChallenge API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -767,23 +781,25 @@ def create_mfa_challenge( api_params = {} if factor is None: raise AppwriteException('Missing required parameter: "factor"') - - api_params['factor'] = self._normalize_value(factor) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaChallenge) - def update_mfa_challenge( self, challenge_id: str, - otp: str + otp: str, ) -> Session: """ Complete the MFA challenge by providing the one-time password. Finish the process of MFA verification by providing the one-time password. To begin the flow, use [createMfaChallenge](/docs/references/cloud/client-web/account#createMfaChallenge) method. @@ -794,12 +810,11 @@ def update_mfa_challenge( ID of the challenge. otp : str Valid verification token. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -810,34 +825,34 @@ def update_mfa_challenge( api_params = {} if challenge_id is None: raise AppwriteException('Missing required parameter: "challenge_id"') - if otp is None: raise AppwriteException('Missing required parameter: "otp"') - - api_params['challengeId'] = self._normalize_value(challenge_id) api_params['otp'] = self._normalize_value(otp) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def list_mfa_factors( - self + self, ) -> MfaFactors: """ List the factors available on the account to be used as a MFA challange. - Returns ------- MfaFactors API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -847,25 +862,28 @@ def list_mfa_factors( api_path = '/account/mfa/factors' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaFactors) - def get_mfa_recovery_codes( - self + self, ) -> MfaRecoveryCodes: """ Get recovery codes that can be used as backup for MFA flow. Before getting codes, they must be generated using [createMfaRecoveryCodes](/docs/references/cloud/client-web/account#createMfaRecoveryCodes) method. An OTP challenge is required to read recovery codes. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -875,25 +893,28 @@ def get_mfa_recovery_codes( api_path = '/account/mfa/recovery-codes' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def create_mfa_recovery_codes( - self + self, ) -> MfaRecoveryCodes: """ Generate recovery codes as backup for MFA flow. It's recommended to generate and show then immediately after user successfully adds their authehticator. Recovery codes can be used as a MFA verification type in [createMfaChallenge](/docs/references/cloud/client-web/account#createMfaChallenge) method. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -903,26 +924,29 @@ def create_mfa_recovery_codes( api_path = '/account/mfa/recovery-codes' api_params = {} - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def update_mfa_recovery_codes( - self + self, ) -> MfaRecoveryCodes: """ Regenerate recovery codes that can be used as backup for MFA flow. Before regenerating codes, they must be first generated using [createMfaRecoveryCodes](/docs/references/cloud/client-web/account#createMfaRecoveryCodes) method. An OTP challenge is required to regenreate recovery codes. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -932,19 +956,23 @@ def update_mfa_recovery_codes( api_path = '/account/mfa/recovery-codes' api_params = {} - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def update_name( self, name: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update currently logged in user account name. @@ -953,15 +981,14 @@ def update_name( ---------- name : str User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -972,24 +999,26 @@ def update_name( api_params = {} if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['name'] = self._normalize_value(name) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_password( self, password: str, old_password: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update currently logged in user password. For validation, user is required to pass in the new password, and the old password. For users created with OAuth, Team Invites and Magic URL, oldPassword is optional. @@ -1000,15 +1029,14 @@ def update_password( New user password. Must be at least 8 chars. old_password : Optional[str] Current user password. Max length: 256 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1019,26 +1047,28 @@ def update_password( api_params = {} if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['password'] = self._normalize_value(password) if old_password is not None: api_params['oldPassword'] = self._normalize_value(old_password) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_phone( self, phone: str, password: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the currently logged in user's phone number. After updating the phone number, the phone verification status will be reset. A confirmation SMS is not sent automatically, however you can use the [POST /account/verification/phone](https://appwrite.io/docs/references/cloud/client-web/account#createPhoneVerification) endpoint to send a confirmation SMS. @@ -1049,15 +1079,14 @@ def update_phone( Phone number. Format this number with a leading '+' and a country code, e.g., +16175551212. password : str User password. Must be at least 8 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1068,41 +1097,41 @@ def update_phone( api_params = {} if phone is None: raise AppwriteException('Missing required parameter: "phone"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['phone'] = self._normalize_value(phone) api_params['password'] = self._normalize_value(password) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def get_prefs( self, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Preferences[T]: """ Get the preferences as a key-value object for the currently logged in user. Parameters ---------- - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Preferences[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1112,18 +1141,22 @@ def get_prefs( api_path = '/account/prefs' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Preferences.with_data(response, model_type) - def update_prefs( self, prefs: Dict[str, Any], - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update currently logged in user account preferences. The object you pass is stored as is, and replaces any previous value. The maximum allowed prefs size is 64kB and throws error if exceeded. @@ -1132,15 +1165,14 @@ def update_prefs( ---------- prefs : Dict[str, Any] Prefs key-value JSON object. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1151,23 +1183,25 @@ def update_prefs( api_params = {} if prefs is None: raise AppwriteException('Missing required parameter: "prefs"') - - api_params['prefs'] = self._normalize_value(prefs) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_recovery( self, email: str, - url: str + url: str, ) -> Token: """ Sends the user an email with a temporary secret key for password reset. When the user clicks the confirmation link he is redirected back to your app password reset URL with the secret key and email address values attached to the URL query string. Use the query string params to submit a request to the [PUT /account/recovery](https://appwrite.io/docs/references/cloud/client-web/account#updateRecovery) endpoint to complete the process. The verification link sent to the user's email address is valid for 1 hour. @@ -1178,12 +1212,11 @@ def create_recovery( User email. url : str URL to redirect the user back to your app from the recovery email. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1194,32 +1227,33 @@ def create_recovery( api_params = {} if email is None: raise AppwriteException('Missing required parameter: "email"') - if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['email'] = self._normalize_value(email) api_params['url'] = self._normalize_value(url) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def update_recovery( self, user_id: str, secret: str, - password: str + password: str, ) -> Token: """ Use this endpoint to complete the user account password reset. Both the **userId** and **secret** arguments will be passed as query parameters to the redirect URL you have provided when sending your request to the [POST /account/recovery](https://appwrite.io/docs/references/cloud/client-web/account#createRecovery) endpoint. - + Please note that in order to avoid a [Redirect Attack](https://github.com/OWASP/CheatSheetSeries/blob/master/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.md) the only valid redirect URLs are the ones from domains you have set when adding your platforms in the console interface. Parameters @@ -1230,12 +1264,11 @@ def update_recovery( Valid reset token. password : str New user password. Must be between 8 and 256 chars. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1246,38 +1279,37 @@ def update_recovery( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) api_params['password'] = self._normalize_value(password) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def list_sessions( - self + self, ) -> SessionList: """ Get the list of active sessions across different devices for the currently logged in user. - Returns ------- SessionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1287,25 +1319,28 @@ def list_sessions( api_path = '/account/sessions' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SessionList) - def delete_sessions( - self + self, ) -> Dict[str, Any]: """ Delete all sessions from the user account and remove any sessions cookies from the end client. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1315,25 +1350,28 @@ def delete_sessions( api_path = '/account/sessions' api_params = {} - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_anonymous_session( - self + self, ) -> Session: """ Use this endpoint to allow a new user to register an anonymous account in your project. This route will also create a new session for the user. To allow the new user to convert an anonymous account to a normal account, you need to update its [email and password](https://appwrite.io/docs/references/cloud/client-web/account#updateEmail) or create an [OAuth2 session](https://appwrite.io/docs/references/cloud/client-web/account#CreateOAuth2Session). - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1343,23 +1381,27 @@ def create_anonymous_session( api_path = '/account/sessions/anonymous' api_params = {} - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def create_email_password_session( self, email: str, - password: str + password: str, ) -> Session: """ Allow the user to login into their account by providing a valid email and password combination. This route will create a new session for the user. - + A user is limited to 10 active sessions at a time by default. [Learn more about session limits](https://appwrite.io/docs/authentication-security#limits). Parameters @@ -1368,12 +1410,11 @@ def create_email_password_session( User email. password : str User password. Must be at least 8 chars. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1384,28 +1425,29 @@ def create_email_password_session( api_params = {} if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - @deprecated("This API has been deprecated since 1.6.0. Please use `account.create_session` instead.") def update_magic_url_session( self, user_id: str, - secret: str + secret: str, ) -> Session: """ Use this endpoint to create a session from token. Provide the **userId** and **secret** parameters from the successful response of authentication flows initiated by token creation. For example, magic URL and phone login. @@ -1418,12 +1460,11 @@ def update_magic_url_session( User ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. secret : str Valid verification token. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1434,28 +1475,29 @@ def update_magic_url_session( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - @deprecated("This API has been deprecated since 1.6.0. Please use `account.create_session` instead.") def update_phone_session( self, user_id: str, - secret: str + secret: str, ) -> Session: """ Use this endpoint to create a session from token. Provide the **userId** and **secret** parameters from the successful response of authentication flows initiated by token creation. For example, magic URL and phone login. @@ -1468,12 +1510,11 @@ def update_phone_session( User ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. secret : str Valid verification token. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1484,27 +1525,28 @@ def update_phone_session( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def create_session( self, user_id: str, - secret: str + secret: str, ) -> Session: """ Use this endpoint to create a session from token. Provide the **userId** and **secret** parameters from the successful response of authentication flows initiated by token creation. For example, magic URL and phone login. @@ -1515,12 +1557,11 @@ def create_session( User ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. secret : str Secret of a token generated by login methods. For example, the `createMagicURLToken` or `createPhoneToken` methods. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1531,26 +1572,27 @@ def create_session( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def get_session( self, - session_id: str + session_id: str, ) -> Session: """ Use this endpoint to get a logged in user's session using a Session ID. Inputting 'current' will return the current session being used. @@ -1559,12 +1601,11 @@ def get_session( ---------- session_id : str Session ID. Use the string 'current' to get the current device session. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1575,21 +1616,23 @@ def get_session( api_params = {} if session_id is None: raise AppwriteException('Missing required parameter: "session_id"') - api_path = api_path.replace('{sessionId}', str(self._normalize_value(session_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def update_session( self, - session_id: str + session_id: str, ) -> Session: """ Use this endpoint to extend a session's length. Extending a session is useful when session expiry is short. If the session was created using an OAuth provider, this endpoint refreshes the access token from the provider. @@ -1598,12 +1641,11 @@ def update_session( ---------- session_id : str Session ID. Use the string 'current' to update the current device session. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1614,22 +1656,24 @@ def update_session( api_params = {} if session_id is None: raise AppwriteException('Missing required parameter: "session_id"') - api_path = api_path.replace('{sessionId}', str(self._normalize_value(session_id))) - - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def delete_session( self, - session_id: str + session_id: str, ) -> Dict[str, Any]: """ Logout the user. Use 'current' as the session ID to logout on this device, use a session ID to logout on another device. If you're looking to logout the user on all devices, use [Delete Sessions](https://appwrite.io/docs/references/cloud/client-web/account#deleteSessions) instead. @@ -1638,12 +1682,11 @@ def delete_session( ---------- session_id : str Session ID. Use the string 'current' to delete the current device session. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1654,36 +1697,37 @@ def delete_session( api_params = {} if session_id is None: raise AppwriteException('Missing required parameter: "session_id"') - api_path = api_path.replace('{sessionId}', str(self._normalize_value(session_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_status( self, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Block the currently logged in user account. Behind the scene, the user record is not deleted but permanently blocked from any access. To completely delete a user, use the Users API instead. Parameters ---------- - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1693,26 +1737,29 @@ def update_status( api_path = '/account/status' api_params = {} - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_email_token( self, user_id: str, email: str, - phrase: Optional[bool] = None + phrase: Optional[bool] = None, ) -> Token: """ Sends the user an email with a secret key for creating a session. If the email address has never been used, a **new account is created** using the provided `userId`. Otherwise, if the email address is already attached to an account, the **user ID is ignored**. Then, the user will receive an email with the one-time password. Use the returned user ID and secret and submit a request to the [POST /v1/account/sessions/token](https://appwrite.io/docs/references/cloud/client-web/account#createSession) endpoint to complete the login process. The secret sent to the user's email is valid for 15 minutes. - + A user is limited to 10 active sessions at a time by default. [Learn more about session limits](https://appwrite.io/docs/authentication-security#limits). - Parameters ---------- @@ -1722,12 +1769,11 @@ def create_email_token( User email. phrase : Optional[bool] Toggle for security phrase. If enabled, email will be send with a randomly generated phrase and the phrase will also be included in the response. Confirming phrases match increases the security of your authentication flow. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1738,37 +1784,37 @@ def create_email_token( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) if phrase is not None: api_params['phrase'] = self._normalize_value(phrase) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def create_magic_url_token( self, user_id: str, email: str, url: Optional[str] = None, - phrase: Optional[bool] = None + phrase: Optional[bool] = None, ) -> Token: """ Sends the user an email with a secret key for creating a session. If the provided user ID has not been registered, a new user will be created. When the user clicks the link in the email, the user is redirected back to the URL you provided with the secret key and userId values attached to the URL query string. Use the query string parameters to submit a request to the [POST /v1/account/sessions/token](https://appwrite.io/docs/references/cloud/client-web/account#createSession) endpoint to complete the login process. The link sent to the user's email address is valid for 1 hour. - + A user is limited to 10 active sessions at a time by default. [Learn more about session limits](https://appwrite.io/docs/authentication-security#limits). - Parameters ---------- @@ -1780,12 +1826,11 @@ def create_magic_url_token( URL to redirect the user back to your app from the magic URL login. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. phrase : Optional[bool] Toggle for security phrase. If enabled, email will be send with a randomly generated phrase and the phrase will also be included in the response. Confirming phrases match increases the security of your authentication flow. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1796,11 +1841,8 @@ def create_magic_url_token( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) if url is not None: @@ -1808,45 +1850,48 @@ def create_magic_url_token( if phrase is not None: api_params['phrase'] = self._normalize_value(phrase) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def create_o_auth2_token( self, provider: OAuthProvider, success: Optional[str] = None, failure: Optional[str] = None, - scopes: Optional[List[str]] = None + scopes: Optional[List[str]] = None, ) -> str: """ - Allow the user to login to their account using the OAuth2 provider of their choice. Each OAuth2 provider should be enabled from the Appwrite console first. Use the success and failure arguments to provide a redirect URL's back to your app when login is completed. - + Allow the user to login to their account using the OAuth2 provider of their choice. Each OAuth2 provider should be enabled from the Appwrite console first. Use the success and failure arguments to provide a redirect URL's back to your app when login is completed. + If authentication succeeds, `userId` and `secret` of a token will be appended to the success URL as query parameters. These can be used to create a new session using the [Create session](https://appwrite.io/docs/references/cloud/client-web/account#createSession) endpoint. - + A user is limited to 10 active sessions at a time by default. [Learn more about session limits](https://appwrite.io/docs/authentication-security#limits). Parameters ---------- provider : OAuthProvider - OAuth2 Provider. Currently, supported providers are: amazon, apple, appwrite, auth0, authentik, autodesk, bitbucket, bitly, box, dailymotion, discord, disqus, dropbox, etsy, facebook, figma, fusionauth, github, gitlab, google, keycloak, kick, linkedin, microsoft, notion, oidc, okta, paypal, paypalSandbox, podio, salesforce, slack, spotify, stripe, tradeshift, tradeshiftBox, twitch, wordpress, x, yahoo, yammer, yandex, zoho, zoom. + OAuth2 Provider. Currently, supported providers are: amazon, apple, appwrite, auth0, authentik, autodesk, bitbucket, bitly, box, dailymotion, discord, disqus, dropbox, etsy, facebook, figma, fusionauth, github, gitlab, google, huggingface, keycloak, kick, linkedin, microsoft, notion, oidc, okta, paypal, paypalSandbox, podio, salesforce, slack, spotify, stripe, tradeshift, tradeshiftBox, twitch, wordpress, x, yahoo, yammer, yandex, zoho, zoom. success : Optional[str] URL to redirect back to your app after a successful login attempt. Only URLs from hostnames in your project's platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. failure : Optional[str] URL to redirect back to your app after a failed login attempt. Only URLs from hostnames in your project's platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. scopes : Optional[List[str]] A list of custom OAuth2 scopes. Check each provider internal docs for a list of supported scopes. Maximum of 100 scopes are allowed, each 4096 characters long. - Returns ------- str Authentication response as a string - + Raises ------ AppwriteException @@ -1857,9 +1902,7 @@ def create_o_auth2_token( api_params = {} if provider is None: raise AppwriteException('Missing required parameter: "provider"') - api_path = api_path.replace('{provider}', str(self._normalize_value(provider))) - if success is not None: api_params['success'] = self._normalize_value(success) if failure is not None: @@ -1867,22 +1910,27 @@ def create_o_auth2_token( if scopes is not None: api_params['scopes'] = self._normalize_value(scopes) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'text/html', - }, api_params, response_type='location') + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'text/html', + }, + api_params, + response_type='location', + ) return response - def create_phone_token( self, user_id: str, - phone: str + phone: str, ) -> Token: """ Sends the user an SMS with a secret key for creating a session. If the provided user ID has not be registered, a new user will be created. Use the returned user ID and secret and submit a request to the [POST /v1/account/sessions/token](https://appwrite.io/docs/references/cloud/client-web/account#createSession) endpoint to complete the login process. The secret sent to the user's phone is valid for 15 minutes. - + A user is limited to 10 active sessions at a time by default. [Learn more about session limits](https://appwrite.io/docs/authentication-security#limits). Parameters @@ -1891,12 +1939,11 @@ def create_phone_token( Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. If the phone number has never been used, a new account is created using the provided userId. Otherwise, if the phone number is already attached to an account, the user ID is ignored. phone : str Phone number. Format this number with a leading '+' and a country code, e.g., +16175551212. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1907,43 +1954,42 @@ def create_phone_token( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if phone is None: raise AppwriteException('Missing required parameter: "phone"') - - api_params['userId'] = self._normalize_value(user_id) api_params['phone'] = self._normalize_value(phone) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def create_email_verification( self, - url: str + url: str, ) -> Token: """ Use this endpoint to send a verification message to your user email address to confirm they are the valid owners of that address. Both the **userId** and **secret** arguments will be passed as query parameters to the URL you have provided to be attached to the verification email. The provided URL should redirect the user back to your app and allow you to complete the verification process by verifying both the **userId** and **secret** parameters. Learn more about how to [complete the verification process](https://appwrite.io/docs/references/cloud/client-web/account#updateVerification). The verification link sent to the user's email address is valid for 7 days. - + Please note that in order to avoid a [Redirect Attack](https://github.com/OWASP/CheatSheetSeries/blob/master/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.md), the only valid redirect URLs are the ones from domains you have set when adding your platforms in the console interface. - Parameters ---------- url : str URL to redirect the user back to your app from the verification email. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1954,29 +2000,30 @@ def create_email_verification( api_params = {} if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['url'] = self._normalize_value(url) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - @deprecated("This API has been deprecated since 1.8.0. Please use `account.create_email_verification` instead.") def create_verification( self, - url: str + url: str, ) -> Token: """ Use this endpoint to send a verification message to your user email address to confirm they are the valid owners of that address. Both the **userId** and **secret** arguments will be passed as query parameters to the URL you have provided to be attached to the verification email. The provided URL should redirect the user back to your app and allow you to complete the verification process by verifying both the **userId** and **secret** parameters. Learn more about how to [complete the verification process](https://appwrite.io/docs/references/cloud/client-web/account#updateVerification). The verification link sent to the user's email address is valid for 7 days. - + Please note that in order to avoid a [Redirect Attack](https://github.com/OWASP/CheatSheetSeries/blob/master/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.md), the only valid redirect URLs are the ones from domains you have set when adding your platforms in the console interface. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `account.create_email_verification` instead. @@ -1984,12 +2031,11 @@ def create_verification( ---------- url : str URL to redirect the user back to your app from the verification email. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2000,23 +2046,25 @@ def create_verification( api_params = {} if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['url'] = self._normalize_value(url) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def update_email_verification( self, user_id: str, - secret: str + secret: str, ) -> Token: """ Use this endpoint to complete the user email verification process. Use both the **userId** and **secret** parameters that were attached to your app URL to verify the user email ownership. If confirmed this route will return a 200 status code. @@ -2027,12 +2075,11 @@ def update_email_verification( User ID. secret : str Valid verification token. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2043,28 +2090,29 @@ def update_email_verification( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - @deprecated("This API has been deprecated since 1.8.0. Please use `account.update_email_verification` instead.") def update_verification( self, user_id: str, - secret: str + secret: str, ) -> Token: """ Use this endpoint to complete the user email verification process. Use both the **userId** and **secret** parameters that were attached to your app URL to verify the user email ownership. If confirmed this route will return a 200 status code. @@ -2077,12 +2125,11 @@ def update_verification( User ID. secret : str Valid verification token. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2093,34 +2140,34 @@ def update_verification( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def create_phone_verification( - self + self, ) -> Token: """ Use this endpoint to send a verification SMS to the currently logged in user. This endpoint is meant for use after updating a user's phone number using the [accountUpdatePhone](https://appwrite.io/docs/references/cloud/client-web/account#updatePhone) endpoint. Learn more about how to [complete the verification process](https://appwrite.io/docs/references/cloud/client-web/account#updatePhoneVerification). The verification code sent to the user's phone number is valid for 15 minutes. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2130,19 +2177,23 @@ def create_phone_verification( api_path = '/account/verifications/phone' api_params = {} - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def update_phone_verification( self, user_id: str, - secret: str + secret: str, ) -> Token: """ Use this endpoint to complete the user phone verification process. Use the **userId** and **secret** that were sent to your user's phone number to verify the user email ownership. If confirmed this route will return a 200 status code. @@ -2153,12 +2204,11 @@ def update_phone_verification( User ID. secret : str Valid verification token. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2169,19 +2219,20 @@ def update_phone_verification( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - diff --git a/appwrite/services/activities.py b/appwrite/services/activities.py index a534716d..9ef1b8d8 100644 --- a/appwrite/services/activities.py +++ b/appwrite/services/activities.py @@ -6,6 +6,7 @@ from ..models.activity_event_list import ActivityEventList from ..models.activity_event import ActivityEvent + class Activities(Service): def __init__(self, client) -> None: @@ -13,7 +14,7 @@ def __init__(self, client) -> None: def list_events( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> ActivityEventList: """ List all events for selected filters. @@ -22,12 +23,11 @@ def list_events( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/databases#querying-documents). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on attributes such as userId, teamId, etc. - Returns ------- ActivityEventList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -36,36 +36,37 @@ def list_events( api_path = '/activities/events' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ActivityEventList) - def get_event( self, - event_id: str + event_id: str, ) -> ActivityEvent: """ Get event by ID. - Parameters ---------- event_id : str Event ID. - Returns ------- ActivityEvent API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -76,14 +77,16 @@ def get_event( api_params = {} if event_id is None: raise AppwriteException('Missing required parameter: "event_id"') - api_path = api_path.replace('{eventId}', str(self._normalize_value(event_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ActivityEvent) - diff --git a/appwrite/services/advisor.py b/appwrite/services/advisor.py index 249e3b76..4afa6aa6 100644 --- a/appwrite/services/advisor.py +++ b/appwrite/services/advisor.py @@ -8,6 +8,7 @@ from ..models.insight_list import InsightList from ..models.insight import Insight + class Advisor(Service): def __init__(self, client) -> None: @@ -16,11 +17,10 @@ def __init__(self, client) -> None: def list_reports( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ReportList: """ Get a list of all the project's analyzer reports. You can use the query params to filter your results. - Parameters ---------- @@ -28,12 +28,11 @@ def list_reports( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: appId, type, targetType, target, analyzedAt total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ReportList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -42,38 +41,39 @@ def list_reports( api_path = '/reports' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ReportList) - def get_report( self, - report_id: str + report_id: str, ) -> Report: """ Get an analyzer report by its unique ID. The response includes the report's metadata and the nested insights it produced. - Parameters ---------- report_id : str Report ID. - Returns ------- Report API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -84,36 +84,36 @@ def get_report( api_params = {} if report_id is None: raise AppwriteException('Missing required parameter: "report_id"') - api_path = api_path.replace('{reportId}', str(self._normalize_value(report_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Report) - def delete_report( self, - report_id: str + report_id: str, ) -> Dict[str, Any]: """ Delete an analyzer report by its unique ID. Nested insights and CTA metadata are removed asynchronously by the deletes worker. - Parameters ---------- report_id : str Report ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -124,27 +124,28 @@ def delete_report( api_params = {} if report_id is None: raise AppwriteException('Missing required parameter: "report_id"') - api_path = api_path.replace('{reportId}', str(self._normalize_value(report_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_insights( self, report_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> InsightList: """ List the insights produced under a single analyzer report. You can use the query params to filter your results further. - Parameters ---------- @@ -154,12 +155,11 @@ def list_insights( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: type, severity, status, resourceType, resourceId, parentResourceType, parentResourceId, analyzedAt, dismissedAt, dismissedBy total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- InsightList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -170,30 +170,31 @@ def list_insights( api_params = {} if report_id is None: raise AppwriteException('Missing required parameter: "report_id"') - api_path = api_path.replace('{reportId}', str(self._normalize_value(report_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=InsightList) - def get_insight( self, report_id: str, - insight_id: str + insight_id: str, ) -> Insight: """ Get an insight by its unique ID, scoped to its parent report. - Parameters ---------- @@ -201,12 +202,11 @@ def get_insight( Parent report ID. insight_id : str Insight ID. - Returns ------- Insight API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -217,18 +217,19 @@ def get_insight( api_params = {} if report_id is None: raise AppwriteException('Missing required parameter: "report_id"') - if insight_id is None: raise AppwriteException('Missing required parameter: "insight_id"') - api_path = api_path.replace('{reportId}', str(self._normalize_value(report_id))) api_path = api_path.replace('{insightId}', str(self._normalize_value(insight_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Insight) - diff --git a/appwrite/services/apps.py b/appwrite/services/apps.py index bd0e6f90..71b5b2ca 100644 --- a/appwrite/services/apps.py +++ b/appwrite/services/apps.py @@ -15,6 +15,7 @@ from ..models.app_secret_plaintext import AppSecretPlaintext from ..models.app_secret import AppSecret + class Apps(Service): def __init__(self, client) -> None: @@ -23,7 +24,7 @@ def __init__(self, client) -> None: def list( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppsList: """ List applications. @@ -34,12 +35,11 @@ def list( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppsList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -48,20 +48,23 @@ def list( api_path = '/apps' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppsList) - def create( self, app_id: str, @@ -82,7 +85,7 @@ def create( enabled: Optional[bool] = None, type: Optional[str] = None, device_flow: Optional[bool] = None, - team_id: Optional[str] = None + team_id: Optional[str] = None, ) -> App: """ Create a new application. @@ -127,12 +130,11 @@ def create( Allow this client to use the OAuth2 Device Authorization Grant (RFC 8628) for input-constrained devices such as TVs and CLIs. Defaults to false. team_id : Optional[str] Team unique ID. - Returns ------- App API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -143,14 +145,10 @@ def create( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if redirect_uris is None: raise AppwriteException('Missing required parameter: "redirect_uris"') - - api_params['appId'] = self._normalize_value(app_id) api_params['name'] = self._normalize_value(name) if description is not None: @@ -187,26 +185,29 @@ def create( if team_id is not None: api_params['teamId'] = self._normalize_value(team_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=App) - def list_installation_scopes( - self + self, ) -> AppScopeList: """ List scopes an application can request when installed on a team. - Returns ------- AppScopeList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -216,25 +217,28 @@ def list_installation_scopes( api_path = '/apps/scopes/installations' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppScopeList) - def list_o_auth2_scopes( - self + self, ) -> AppScopeList: """ List scopes an application can request during the OAuth2 flow. - Returns ------- AppScopeList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -244,17 +248,21 @@ def list_o_auth2_scopes( api_path = '/apps/scopes/oauth2' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppScopeList) - def get( self, - app_id: str + app_id: str, ) -> App: """ Get an application by its unique ID. @@ -263,12 +271,11 @@ def get( ---------- app_id : str Application unique ID. - Returns ------- App API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -279,18 +286,20 @@ def get( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=App) - def update( self, app_id: str, @@ -312,7 +321,7 @@ def update( type: Optional[str] = None, device_flow: Optional[bool] = None, installation_scopes: Optional[List[str]] = None, - installation_redirect_url: Optional[str] = None + installation_redirect_url: Optional[str] = None, ) -> App: """ Update an application by its unique ID. @@ -359,12 +368,11 @@ def update( Scopes the application requests when installed on a team. Only scopes allowed by the project's OAuth2 server installation scopes configuration are accepted; use the list installation scopes endpoint to discover available values. Maximum of 100 scopes are allowed. installation_redirect_url : Optional[str] URL users are redirected to after creating or updating an installation of this application. Must be an https URL, an http loopback URL (localhost, 127.0.0.1, [::1]), or a private-use scheme URI, and must not contain a fragment. Leave empty for no redirect. - Returns ------- App API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -375,12 +383,9 @@ def update( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - api_params['name'] = self._normalize_value(name) if description is not None: api_params['description'] = self._normalize_value(description) @@ -419,18 +424,22 @@ def update( if installation_redirect_url is not None: api_params['installationRedirectUrl'] = self._normalize_value(installation_redirect_url) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=App) - def delete( self, - app_id: str + app_id: str, ) -> Dict[str, Any]: """ Delete an application by its unique ID. @@ -439,12 +448,11 @@ def delete( ---------- app_id : str Application unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -455,24 +463,26 @@ def delete( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_installations( self, app_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppInstallationList: """ List installations of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. @@ -485,12 +495,11 @@ def list_installations( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppInstallationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -501,26 +510,28 @@ def list_installations( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallationList) - def get_installation( self, app_id: str, - installation_id: str + installation_id: str, ) -> AppInstallation: """ Get an installation of an application by its unique ID. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. @@ -531,12 +542,11 @@ def get_installation( Application unique ID. installation_id : str Installation unique ID. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -547,26 +557,27 @@ def get_installation( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def delete_installation( self, app_id: str, - installation_id: str + installation_id: str, ) -> Dict[str, Any]: """ Delete an installation of an application by its unique ID. Requires a caller with update access to the app. Previously issued installation access tokens are revoked. @@ -577,12 +588,11 @@ def delete_installation( Application unique ID. installation_id : str Installation unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -593,27 +603,28 @@ def delete_installation( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def create_installation_token( self, app_id: str, - installation_id: str + installation_id: str, ) -> Oauth2Token: """ Create a token for an installation of an application. Requires an app key sent in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header, or a caller with update access to the app. The returned token carries the scopes and authorization details granted to the installation, and can be used as an `Authorization: Bearer` header everywhere OAuth2 access tokens are accepted. Multiple tokens can be active for the same installation at once; each token stays valid until it expires or the installation is updated or deleted. @@ -624,12 +635,11 @@ def create_installation_token( Application unique ID. installation_id : str Installation unique ID. - Returns ------- Oauth2Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -640,28 +650,29 @@ def create_installation_token( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Token) - def list_keys( self, app_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppKeyList: """ List app keys for an application. @@ -674,12 +685,11 @@ def list_keys( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppKeyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -690,25 +700,27 @@ def list_keys( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppKeyList) - def create_key( self, - app_id: str + app_id: str, ) -> AppKey: """ Create a new app key for an application. App keys carry no scopes; send one in the `X-Appwrite-Key` header alongside the `X-Appwrite-App` header to list the application's installations and create installation access tokens. @@ -717,12 +729,11 @@ def create_key( ---------- app_id : str Application unique ID. - Returns ------- AppKey API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -733,23 +744,25 @@ def create_key( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppKey) - def get_key( self, app_id: str, - key_id: str + key_id: str, ) -> AppKey: """ Get an app key by its unique ID. @@ -760,12 +773,11 @@ def get_key( Application unique ID. key_id : str App key unique ID. - Returns ------- AppKey API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -776,26 +788,27 @@ def get_key( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppKey) - def delete_key( self, app_id: str, - key_id: str + key_id: str, ) -> Dict[str, Any]: """ Delete an app key by its unique ID. @@ -806,12 +819,11 @@ def delete_key( Application unique ID. key_id : str App key unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -822,27 +834,28 @@ def delete_key( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def update_labels( self, app_id: str, - labels: List[str] + labels: List[str], ) -> App: """ Update the labels of an application. Labels are read-only for clients; only a server SDK using a project API key can set them. Replaces the previous labels. @@ -853,12 +866,11 @@ def update_labels( Application unique ID. labels : List[str] Array of application labels. Replaces the previous labels. Maximum of 1000 labels are allowed, each up to 36 alphanumeric characters long. - Returns ------- App API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -869,28 +881,29 @@ def update_labels( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if labels is None: raise AppwriteException('Missing required parameter: "labels"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - api_params['labels'] = self._normalize_value(labels) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=App) - def list_secrets( self, app_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppSecretList: """ List client secrets for an application. @@ -903,12 +916,11 @@ def list_secrets( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppSecretList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -919,25 +931,27 @@ def list_secrets( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppSecretList) - def create_secret( self, - app_id: str + app_id: str, ) -> AppSecretPlaintext: """ Create a new client secret for an application. @@ -946,12 +960,11 @@ def create_secret( ---------- app_id : str Application unique ID. - Returns ------- AppSecretPlaintext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -962,23 +975,25 @@ def create_secret( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppSecretPlaintext) - def get_secret( self, app_id: str, - secret_id: str + secret_id: str, ) -> AppSecret: """ Get an application client secret by its unique ID. @@ -989,12 +1004,11 @@ def get_secret( Application unique ID. secret_id : str Secret unique ID. - Returns ------- AppSecret API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1005,26 +1019,27 @@ def get_secret( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if secret_id is None: raise AppwriteException('Missing required parameter: "secret_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{secretId}', str(self._normalize_value(secret_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppSecret) - def delete_secret( self, app_id: str, - secret_id: str + secret_id: str, ) -> Dict[str, Any]: """ Delete an application client secret by its unique ID. @@ -1035,12 +1050,11 @@ def delete_secret( Application unique ID. secret_id : str Secret unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1051,27 +1065,28 @@ def delete_secret( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if secret_id is None: raise AppwriteException('Missing required parameter: "secret_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) api_path = api_path.replace('{secretId}', str(self._normalize_value(secret_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def update_team( self, app_id: str, - team_id: str + team_id: str, ) -> App: """ Transfer an application to another team by its unique ID. @@ -1082,12 +1097,11 @@ def update_team( Application unique ID. team_id : str Team ID of the team to transfer application to. - Returns ------- App API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1098,26 +1112,27 @@ def update_team( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - api_params['teamId'] = self._normalize_value(team_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=App) - def delete_tokens( self, - app_id: str + app_id: str, ) -> Dict[str, Any]: """ Revoke all tokens for an application by its unique ID. @@ -1126,12 +1141,11 @@ def delete_tokens( ---------- app_id : str Application unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1142,15 +1156,17 @@ def delete_tokens( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{appId}', str(self._normalize_value(app_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/avatars.py b/appwrite/services/avatars.py index 5200f9dd..ab7223af 100644 --- a/appwrite/services/avatars.py +++ b/appwrite/services/avatars.py @@ -11,6 +11,7 @@ from ..enums.browser_permission import BrowserPermission from ..enums.image_format import ImageFormat + class Avatars(Service): def __init__(self, client) -> None: @@ -21,11 +22,11 @@ def get_browser( code: Browser, width: Optional[float] = None, height: Optional[float] = None, - quality: Optional[float] = None + quality: Optional[float] = None, ) -> bytes: """ You can use this endpoint to show different browser icons to your users. The code argument receives the browser code as it appears in your user [GET /account/sessions](https://appwrite.io/docs/references/cloud/client-web/account#getSessions) endpoint. Use width, height and quality arguments to change the output settings. - + When one dimension is specified and the other is 0, the image is scaled with preserved aspect ratio. If both dimensions are 0, the API provides an image at source quality. If dimensions are not specified, the default size of image returned is 100x100px. Parameters @@ -38,12 +39,11 @@ def get_browser( Image height. Pass an integer between 0 to 2000. Defaults to 100. quality : Optional[float] Image quality. Pass an integer between 0 to 100. Defaults to keep existing image quality. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -54,9 +54,7 @@ def get_browser( api_params = {} if code is None: raise AppwriteException('Missing required parameter: "code"') - api_path = api_path.replace('{code}', str(self._normalize_value(code))) - if width is not None: api_params['width'] = self._normalize_value(width) if height is not None: @@ -64,26 +62,29 @@ def get_browser( if quality is not None: api_params['quality'] = self._normalize_value(quality) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response - def get_credit_card( self, code: CreditCard, width: Optional[float] = None, height: Optional[float] = None, - quality: Optional[float] = None + quality: Optional[float] = None, ) -> bytes: """ The credit card endpoint will return you the icon of the credit card provider you need. Use width, height and quality arguments to change the output settings. - + When one dimension is specified and the other is 0, the image is scaled with preserved aspect ratio. If both dimensions are 0, the API provides an image at source quality. If dimensions are not specified, the default size of image returned is 100x100px. - Parameters ---------- @@ -95,12 +96,11 @@ def get_credit_card( Image height. Pass an integer between 0 to 2000. Defaults to 100. quality : Optional[float] Image quality. Pass an integer between 0 to 100. Defaults to keep existing image quality. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -111,9 +111,7 @@ def get_credit_card( api_params = {} if code is None: raise AppwriteException('Missing required parameter: "code"') - api_path = api_path.replace('{code}', str(self._normalize_value(code))) - if width is not None: api_params['width'] = self._normalize_value(width) if height is not None: @@ -121,33 +119,36 @@ def get_credit_card( if quality is not None: api_params['quality'] = self._normalize_value(quality) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response - def get_favicon( self, - url: str + url: str, ) -> bytes: """ Use this endpoint to fetch the favorite icon (AKA favicon) of any remote website URL. - + This endpoint does not follow HTTP redirects. Parameters ---------- url : str Website URL which you want to fetch the favicon from. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -158,30 +159,31 @@ def get_favicon( api_params = {} if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['url'] = self._normalize_value(url) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/*', + }, + api_params, + ) return response - def get_flag( self, code: Flag, width: Optional[float] = None, height: Optional[float] = None, - quality: Optional[float] = None + quality: Optional[float] = None, ) -> bytes: """ You can use this endpoint to show different country flags icons to your users. The code argument receives the 2 letter country code. Use width, height and quality arguments to change the output settings. Country codes follow the [ISO 3166-1](https://en.wikipedia.org/wiki/ISO_3166-1) standard. - + When one dimension is specified and the other is 0, the image is scaled with preserved aspect ratio. If both dimensions are 0, the API provides an image at source quality. If dimensions are not specified, the default size of image returned is 100x100px. - Parameters ---------- @@ -193,12 +195,11 @@ def get_flag( Image height. Pass an integer between 0 to 2000. Defaults to 100. quality : Optional[float] Image quality. Pass an integer between 0 to 100. Defaults to keep existing image quality. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -209,9 +210,7 @@ def get_flag( api_params = {} if code is None: raise AppwriteException('Missing required parameter: "code"') - api_path = api_path.replace('{code}', str(self._normalize_value(code))) - if width is not None: api_params['width'] = self._normalize_value(width) if height is not None: @@ -219,25 +218,29 @@ def get_flag( if quality is not None: api_params['quality'] = self._normalize_value(quality) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response - def get_image( self, url: str, width: Optional[float] = None, - height: Optional[float] = None + height: Optional[float] = None, ) -> bytes: """ Use this endpoint to fetch a remote image URL and crop it to any image size you want. This endpoint is very useful if you need to crop and display remote images in your app or in case you want to make sure a 3rd party image is properly served using a TLS protocol. - + When one dimension is specified and the other is 0, the image is scaled with preserved aspect ratio. If both dimensions are 0, the API provides an image at source quality. If dimensions are not specified, the default size of image returned is 400x400px. - + This endpoint does not follow HTTP redirects. Parameters @@ -248,12 +251,11 @@ def get_image( Resize preview image width, Pass an integer between 0 to 2000. Defaults to 400. height : Optional[float] Resize preview image height, Pass an integer between 0 to 2000. Defaults to 400. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -264,36 +266,37 @@ def get_image( api_params = {} if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['url'] = self._normalize_value(url) if width is not None: api_params['width'] = self._normalize_value(width) if height is not None: api_params['height'] = self._normalize_value(height) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/*', + }, + api_params, + ) return response - def get_initials( self, name: Optional[str] = None, width: Optional[float] = None, height: Optional[float] = None, - background: Optional[str] = None + background: Optional[str] = None, ) -> bytes: """ Use this endpoint to show your user initials avatar icon on your website or app. By default, this route will try to print your logged-in user name or email initials. You can also overwrite the user name if you pass the 'name' parameter. If no name is given and no user is logged, an empty avatar will be returned. - + You can use the color and background params to change the avatar colors. By default, a random theme will be selected. The random theme will persist for the user's initials when reloading the same theme will always return for the same initials. - + When one dimension is specified and the other is 0, the image is scaled with preserved aspect ratio. If both dimensions are 0, the API provides an image at source quality. If dimensions are not specified, the default size of image returned is 100x100px. - Parameters ---------- @@ -305,12 +308,11 @@ def get_initials( Image height. Pass an integer between 0 to 2000. Defaults to 100. background : Optional[str] Changes background color. By default a random color will be picked and stay will persistent to the given name. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -319,7 +321,6 @@ def get_initials( api_path = '/avatars/initials' api_params = {} - if name is not None: api_params['name'] = self._normalize_value(name) if width is not None: @@ -329,24 +330,103 @@ def get_initials( if background is not None: api_params['background'] = self._normalize_value(background) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response + def get_photo( + self, + width: Optional[float] = None, + height: Optional[float] = None, + quality: Optional[float] = None, + output: Optional[str] = None, + rating: Optional[str] = None, + user_id: Optional[str] = None, + email_hash: Optional[str] = None, + name: Optional[str] = None, + ) -> bytes: + """ + Returns the best available profile photo for a user. The endpoint tries each source in priority order and returns the first successful result: OAuth2 identity photo, Gravatar, Libravatar, Appwrite Initials, built-in static fallback. + + The photo resolves for the currently authenticated user unless `userId` points at another user. Passing `emailHash` and/or `name` resolves the avatar from those values alone: the hash is looked up on Gravatar and Libravatar, the name is rendered as initials, and the user's own identity photos, email, and name leave the chain so they never shadow the avatar being asked for. Emails are only ever accepted pre-hashed, so no address ends up in a URL. + + Parameters + ---------- + width : Optional[float] + Output image width in pixels. Pass an integer between 0 and 2000. Defaults to 256. + height : Optional[float] + Output image height in pixels. Pass an integer between 0 and 2000. Defaults to 256. + quality : Optional[float] + Output image quality between 0 and 100. Defaults to 100. + output : Optional[str] + Output image format. Defaults to 'png'. + rating : Optional[str] + Maximum image rating to fetch from Gravatar/Libravatar. Defaults to 'g'. + user_id : Optional[str] + User ID to resolve the photo for. Defaults to 'current()' for the currently authenticated user. + email_hash : Optional[str] + SHA256 hash of the lowercase, trimmed email address to look up on Gravatar and Libravatar instead of the user's own photo sources. Pass the hash, never the address itself. + name : Optional[str] + Name to render initials from instead of the user's own photo sources. Max length: 128 chars. + Returns + ------- + bytes + Response as bytes + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/avatars/photo' + api_params = {} + if width is not None: + api_params['width'] = self._normalize_value(width) + if height is not None: + api_params['height'] = self._normalize_value(height) + if quality is not None: + api_params['quality'] = self._normalize_value(quality) + if output is not None: + api_params['output'] = self._normalize_value(output) + if rating is not None: + api_params['rating'] = self._normalize_value(rating) + if user_id is not None: + api_params['userId'] = self._normalize_value(user_id) + if email_hash is not None: + api_params['emailHash'] = self._normalize_value(email_hash) + if name is not None: + api_params['name'] = self._normalize_value(name) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/*', + }, + api_params, + ) + + return response def get_qr( self, text: str, size: Optional[float] = None, margin: Optional[float] = None, - download: Optional[bool] = None + download: Optional[bool] = None, ) -> bytes: """ Converts a given plain text to a QR code image. You can use the query parameters to change the size and style of the resulting image. - Parameters ---------- @@ -358,12 +438,11 @@ def get_qr( Margin from edge. Pass an integer between 0 to 10. Defaults to 1. download : Optional[bool] Return resulting image with 'Content-Disposition: attachment ' headers for the browser to start downloading it. Pass 0 for no header, or 1 for otherwise. Default value is set to 0. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -374,8 +453,6 @@ def get_qr( api_params = {} if text is None: raise AppwriteException('Missing required parameter: "text"') - - api_params['text'] = self._normalize_value(text) if size is not None: api_params['size'] = self._normalize_value(size) @@ -384,14 +461,18 @@ def get_qr( if download is not None: api_params['download'] = self._normalize_value(download) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response - def get_screenshot( self, url: str, @@ -413,13 +494,13 @@ def get_screenshot( width: Optional[float] = None, height: Optional[float] = None, quality: Optional[float] = None, - output: Optional[ImageFormat] = None + output: Optional[ImageFormat] = None, ) -> bytes: """ Use this endpoint to capture a screenshot of any website URL. This endpoint uses a headless browser to render the webpage and capture it as an image. - + You can configure the browser viewport size, theme, user agent, geolocation, permissions, and more. Capture either just the viewport or the full page scroll. - + When width and height are specified, the image is resized accordingly. If both dimensions are 0, the API provides an image at original size. If dimensions are not specified, the default viewport size is 1280x720px. Parameters @@ -464,12 +545,11 @@ def get_screenshot( Screenshot quality. Pass an integer between 0 to 100. Defaults to keep existing image quality. output : Optional[ImageFormat] Output format type (jpeg, jpg, png, gif and webp). - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -480,8 +560,6 @@ def get_screenshot( api_params = {} if url is None: raise AppwriteException('Missing required parameter: "url"') - - api_params['url'] = self._normalize_value(url) if headers is not None: api_params['headers'] = self._normalize_value(headers) @@ -522,10 +600,14 @@ def get_screenshot( if output is not None: api_params['output'] = self._normalize_value(output) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/png', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/png', + }, + api_params, + ) return response - diff --git a/appwrite/services/backups.py b/appwrite/services/backups.py index cc41ff09..4d40755e 100644 --- a/appwrite/services/backups.py +++ b/appwrite/services/backups.py @@ -11,6 +11,7 @@ from ..models.backup_restoration import BackupRestoration from ..models.backup_restoration_list import BackupRestorationList + class Backups(Service): def __init__(self, client) -> None: @@ -18,7 +19,7 @@ def __init__(self, client) -> None: def list_archives( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> BackupArchiveList: """ List all archives for a project. @@ -27,12 +28,11 @@ def list_archives( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. - Returns ------- BackupArchiveList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -41,22 +41,25 @@ def list_archives( api_path = '/backups/archives' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupArchiveList) - def create_archive( self, services: List[BackupServices], - resource_id: Optional[str] = None + resource_id: Optional[str] = None, ) -> BackupArchive: """ Create a new archive asynchronously for a project. @@ -67,12 +70,11 @@ def create_archive( Array of services to backup resource_id : Optional[str] Resource ID. When set, only this single resource will be backed up. - Returns ------- BackupArchive API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -83,24 +85,26 @@ def create_archive( api_params = {} if services is None: raise AppwriteException('Missing required parameter: "services"') - - api_params['services'] = self._normalize_value(services) if resource_id is not None: api_params['resourceId'] = self._normalize_value(resource_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupArchive) - def get_archive( self, - archive_id: str + archive_id: str, ) -> BackupArchive: """ Get a backup archive using it's ID. @@ -109,12 +113,11 @@ def get_archive( ---------- archive_id : str Archive ID. Choose a custom ID`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- BackupArchive API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -125,21 +128,23 @@ def get_archive( api_params = {} if archive_id is None: raise AppwriteException('Missing required parameter: "archive_id"') - api_path = api_path.replace('{archiveId}', str(self._normalize_value(archive_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupArchive) - def delete_archive( self, - archive_id: str + archive_id: str, ) -> Dict[str, Any]: """ Delete an existing archive for a project. @@ -148,12 +153,11 @@ def delete_archive( ---------- archive_id : str Policy ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -164,22 +168,24 @@ def delete_archive( api_params = {} if archive_id is None: raise AppwriteException('Missing required parameter: "archive_id"') - api_path = api_path.replace('{archiveId}', str(self._normalize_value(archive_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_policies( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> BackupPolicyList: """ List all policies for a project. @@ -188,12 +194,11 @@ def list_policies( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. - Returns ------- BackupPolicyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -202,18 +207,21 @@ def list_policies( api_path = '/backups/policies' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupPolicyList) - def create_policy( self, policy_id: str, @@ -222,7 +230,7 @@ def create_policy( schedule: str, name: Optional[str] = None, resource_id: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> BackupPolicy: """ Create a new backup policy. @@ -243,12 +251,11 @@ def create_policy( Resource ID. When set, only this single resource will be backed up. enabled : Optional[bool] Is policy enabled? When set to 'disabled', no backups will be taken - Returns ------- BackupPolicy API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -259,17 +266,12 @@ def create_policy( api_params = {} if policy_id is None: raise AppwriteException('Missing required parameter: "policy_id"') - if services is None: raise AppwriteException('Missing required parameter: "services"') - if retention is None: raise AppwriteException('Missing required parameter: "retention"') - if schedule is None: raise AppwriteException('Missing required parameter: "schedule"') - - api_params['policyId'] = self._normalize_value(policy_id) if name is not None: api_params['name'] = self._normalize_value(name) @@ -281,18 +283,22 @@ def create_policy( api_params['retention'] = self._normalize_value(retention) api_params['schedule'] = self._normalize_value(schedule) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupPolicy) - def get_policy( self, - policy_id: str + policy_id: str, ) -> BackupPolicy: """ Get a backup policy using it's ID. @@ -301,12 +307,11 @@ def get_policy( ---------- policy_id : str Policy ID. Choose a custom ID`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- BackupPolicy API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -317,25 +322,27 @@ def get_policy( api_params = {} if policy_id is None: raise AppwriteException('Missing required parameter: "policy_id"') - api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupPolicy) - def update_policy( self, policy_id: str, name: Optional[str] = None, retention: Optional[float] = None, schedule: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> BackupPolicy: """ Update an existing policy using it's ID. @@ -352,12 +359,11 @@ def update_policy( Cron expression enabled : Optional[bool] Is Backup enabled? When set to 'disabled', No backup will be taken - Returns ------- BackupPolicy API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -368,9 +374,7 @@ def update_policy( api_params = {} if policy_id is None: raise AppwriteException('Missing required parameter: "policy_id"') - api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if retention is not None: @@ -380,18 +384,22 @@ def update_policy( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupPolicy) - def delete_policy( self, - policy_id: str + policy_id: str, ) -> Dict[str, Any]: """ Delete a policy using it's ID. @@ -400,12 +408,11 @@ def delete_policy( ---------- policy_id : str Policy ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -416,37 +423,38 @@ def delete_policy( api_params = {} if policy_id is None: raise AppwriteException('Missing required parameter: "policy_id"') - api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def create_restoration( self, archive_id: str, services: List[BackupServices], new_resource_id: Optional[str] = None, - new_resource_name: Optional[str] = None + new_resource_name: Optional[str] = None, ) -> BackupRestoration: """ Create and trigger a new restoration for a backup on a project. - + For a backup of one database, the restoration resolves its destination before it is queued. When `newResourceId` is omitted, the archived database is restored in place and its own ID is returned in `options`. Pass a different `newResourceId` to restore alongside it as a new database instead. - + The restoration migration records the archived database in `resourceId` and `resourceType`, and the resolved database in `destinationResourceId` and `destinationResourceType`. Database types are stored canonically as `database`, `documentsdb`, or `vectorsdb`. Project-wide restorations leave these fields empty because they do not have a single source or destination database. - + To list every migration related to one database, use its canonical type in a nested `OR(AND(...), AND(...), AND(...))` across the root, parent, and destination relation pairs: `(resourceType, resourceId)`, `(parentResourceType, parentResourceId)`, and `(destinationResourceType, destinationResourceId)`. Legacy and TablesDB databases use `database`; the operational `resourceType` of a table migration is not rewritten to `tablesdb`. - + When restoring a DocumentsDB or VectorsDB database from a dedicated source, the restore provisions a fresh dedicated backing database at the source database's own specification and lands the data there. An in-place restore swaps the database onto that backing only once the restore has succeeded, and retires the backing it displaced only once that swap is confirmed, so the source keeps serving its own data until the restored data is in place and any failure leaves it untouched. A serverless source has no dedicated backing to clone and restores onto the archived database instead. - Parameters ---------- @@ -458,12 +466,11 @@ def create_restoration( Destination resource ID. Omit to restore the archived resource in place, or pass a different ID to restore alongside it as a new resource. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. new_resource_name : Optional[str] Database name. Max length: 128 chars. - Returns ------- BackupRestoration API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -474,11 +481,8 @@ def create_restoration( api_params = {} if archive_id is None: raise AppwriteException('Missing required parameter: "archive_id"') - if services is None: raise AppwriteException('Missing required parameter: "services"') - - api_params['archiveId'] = self._normalize_value(archive_id) api_params['services'] = self._normalize_value(services) if new_resource_id is not None: @@ -486,18 +490,22 @@ def create_restoration( if new_resource_name is not None: api_params['newResourceName'] = self._normalize_value(new_resource_name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupRestoration) - def list_restorations( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> BackupRestorationList: """ List all backup restorations for a project. @@ -506,12 +514,11 @@ def list_restorations( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. - Returns ------- BackupRestorationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -520,21 +527,24 @@ def list_restorations( api_path = '/backups/restorations' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupRestorationList) - def get_restoration( self, - restoration_id: str + restoration_id: str, ) -> BackupRestoration: """ Get the current status of a backup restoration. @@ -543,12 +553,11 @@ def get_restoration( ---------- restoration_id : str Restoration ID. Choose a custom ID`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- BackupRestoration API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -559,14 +568,16 @@ def get_restoration( api_params = {} if restoration_id is None: raise AppwriteException('Missing required parameter: "restoration_id"') - api_path = api_path.replace('{restorationId}', str(self._normalize_value(restoration_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BackupRestoration) - diff --git a/appwrite/services/databases.py b/appwrite/services/databases.py index 32c63923..dde65c10 100644 --- a/appwrite/services/databases.py +++ b/appwrite/services/databases.py @@ -39,6 +39,7 @@ T = TypeVar('T') + class Databases(Service): def __init__(self, client) -> None: @@ -49,7 +50,7 @@ def list( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> DatabaseList: """ Get a list of all databases from the current Appwrite project. You can use the search parameter to filter your results. @@ -64,12 +65,11 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- DatabaseList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -78,7 +78,6 @@ def list( api_path = '/databases' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -86,24 +85,27 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseList) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create` instead.") def create( self, database_id: str, name: str, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Database: """ Create a new Database. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create` instead. @@ -115,12 +117,11 @@ def create( Database name. Max length: 128 chars. enabled : Optional[bool] Is the database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -131,29 +132,30 @@ def create( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['databaseId'] = self._normalize_value(database_id) api_params['name'] = self._normalize_value(name) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.list_transactions` instead.") def list_transactions( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> TransactionList: """ List transactions across all databases. @@ -164,12 +166,11 @@ def list_transactions( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). - Returns ------- TransactionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -178,22 +179,25 @@ def list_transactions( api_path = '/databases/transactions' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TransactionList) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_transaction` instead.") def create_transaction( self, - ttl: Optional[float] = None + ttl: Optional[float] = None, ) -> Transaction: """ Create a new transaction. @@ -204,12 +208,11 @@ def create_transaction( ---------- ttl : Optional[float] Seconds before the transaction expires. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -218,23 +221,26 @@ def create_transaction( api_path = '/databases/transactions' api_params = {} - if ttl is not None: api_params['ttl'] = self._normalize_value(ttl) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get_transaction` instead.") def get_transaction( self, - transaction_id: str + transaction_id: str, ) -> Transaction: """ Get a transaction by its unique ID. @@ -245,12 +251,11 @@ def get_transaction( ---------- transaction_id : str Transaction ID. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -261,24 +266,26 @@ def get_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_transaction` instead.") def update_transaction( self, transaction_id: str, commit: Optional[bool] = None, - rollback: Optional[bool] = None + rollback: Optional[bool] = None, ) -> Transaction: """ Update a transaction, to either commit or roll back its operations. @@ -293,12 +300,11 @@ def update_transaction( Commit transaction? rollback : Optional[bool] Rollback transaction? - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -309,27 +315,29 @@ def update_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - if commit is not None: api_params['commit'] = self._normalize_value(commit) if rollback is not None: api_params['rollback'] = self._normalize_value(rollback) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_transaction` instead.") def delete_transaction( self, - transaction_id: str + transaction_id: str, ) -> Dict[str, Any]: """ Delete a transaction by its unique ID. @@ -340,12 +348,11 @@ def delete_transaction( ---------- transaction_id : str Transaction ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -356,23 +363,25 @@ def delete_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_operations` instead.") def create_operations( self, transaction_id: str, - operations: Optional[List[Dict[str, Any]]] = None + operations: Optional[List[Dict[str, Any]]] = None, ) -> Transaction: """ Create multiple operations in a single transaction. @@ -385,12 +394,11 @@ def create_operations( Transaction ID. operations : Optional[List[Dict[str, Any]]] Array of staged operations. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -401,25 +409,27 @@ def create_operations( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - if operations is not None: api_params['operations'] = self._normalize_value(operations) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get` instead.") def get( self, - database_id: str + database_id: str, ) -> Database: """ Get a database by its unique ID. This endpoint response returns a JSON object with the database metadata. @@ -430,12 +440,11 @@ def get( ---------- database_id : str Database ID. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -446,24 +455,26 @@ def get( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update` instead.") def update( self, database_id: str, name: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Database: """ Update a database by its unique ID. @@ -478,12 +489,11 @@ def update( Database name. Max length: 128 chars. enabled : Optional[bool] Is database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -494,27 +504,29 @@ def update( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete` instead.") def delete( self, - database_id: str + database_id: str, ) -> Dict[str, Any]: """ Delete a database by its unique ID. Only API keys with with databases.write scope can delete a database. @@ -525,12 +537,11 @@ def delete( ---------- database_id : str Database ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -541,25 +552,27 @@ def delete( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.list_tables` instead.") def list_collections( self, database_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> CollectionList: """ Get a list of all collections that belong to the provided databaseId. You can use the search parameter to filter your results. @@ -576,12 +589,11 @@ def list_collections( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- CollectionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -592,9 +604,7 @@ def list_collections( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -602,14 +612,18 @@ def list_collections( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=CollectionList) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_table` instead.") def create_collection( self, @@ -620,7 +634,7 @@ def create_collection( document_security: Optional[bool] = None, enabled: Optional[bool] = None, attributes: Optional[List[Dict[str, Any]]] = None, - indexes: Optional[List[Dict[str, Any]]] = None + indexes: Optional[List[Dict[str, Any]]] = None, ) -> Collection: """ Create a new Collection. Before using this route, you should create a new database resource using either a [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection) API or directly from your database console. @@ -645,12 +659,11 @@ def create_collection( Array of attribute definitions to create. Each attribute should contain: key (string), type (string: string, varchar, text, mediumtext, longtext, integer, bigint, double, boolean, datetime, point, linestring, polygon, email, url, ip, enum), size (integer, required for string and varchar types), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. indexes : Optional[List[Dict[str, Any]]] Array of index definitions to create. Each index should contain: key (string), type (string: key, fulltext, unique, spatial), attributes (array of attribute keys), orders (array of ASC/DESC, optional), and lengths (array of integers, optional). - Returns ------- Collection API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -661,15 +674,11 @@ def create_collection( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - api_params['collectionId'] = self._normalize_value(collection_id) api_params['name'] = self._normalize_value(name) if permissions is not None: @@ -683,20 +692,24 @@ def create_collection( if indexes is not None: api_params['indexes'] = self._normalize_value(indexes) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Collection) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get_table` instead.") def get_collection( self, database_id: str, - collection_id: str + collection_id: str, ) -> Collection: """ Get a collection by its unique ID. This endpoint response returns a JSON object with the collection metadata. @@ -709,12 +722,11 @@ def get_collection( Database ID. collection_id : str Collection ID. - Returns ------- Collection API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -725,22 +737,23 @@ def get_collection( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Collection) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_table` instead.") def update_collection( self, @@ -750,7 +763,7 @@ def update_collection( permissions: Optional[List[str]] = None, document_security: Optional[bool] = None, enabled: Optional[bool] = None, - purge: Optional[bool] = None + purge: Optional[bool] = None, ) -> Collection: """ Update a collection by its unique ID. @@ -773,12 +786,11 @@ def update_collection( Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. purge : Optional[bool] When true, purge all cached list responses for this collection as part of the update. Use this to force readers to see fresh data immediately instead of waiting for the cache TTL to expire. - Returns ------- Collection API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -789,13 +801,10 @@ def update_collection( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if permissions is not None: @@ -807,20 +816,24 @@ def update_collection( if purge is not None: api_params['purge'] = self._normalize_value(purge) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Collection) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_table` instead.") def delete_collection( self, database_id: str, - collection_id: str + collection_id: str, ) -> Dict[str, Any]: """ Delete a collection by its unique ID. Only users with write permissions have access to delete this resource. @@ -833,12 +846,11 @@ def delete_collection( Database ID. collection_id : str Collection ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -849,29 +861,30 @@ def delete_collection( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.list_columns` instead.") def list_attributes( self, database_id: str, collection_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AttributeList: """ List attributes in the collection. @@ -888,12 +901,11 @@ def list_attributes( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, type, size, required, array, status, error total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AttributeList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -904,26 +916,27 @@ def list_attributes( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeList) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_big_int_column` instead.") def create_big_int_attribute( self, @@ -934,11 +947,10 @@ def create_big_int_attribute( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeBigint: """ Create a bigint attribute. Optionally, minimum and maximum values can be provided. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_big_int_column` instead. @@ -960,12 +972,11 @@ def create_big_int_attribute( Default value. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeBigint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -976,19 +987,14 @@ def create_big_int_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -1000,15 +1006,19 @@ def create_big_int_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeBigint) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_big_int_column` instead.") def update_big_int_attribute( self, @@ -1019,11 +1029,10 @@ def update_big_int_attribute( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeBigint: """ Update a bigint attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_big_int_column` instead. @@ -1045,12 +1054,11 @@ def update_big_int_attribute( Maximum value new_key : Optional[str] New Attribute Key. - Returns ------- AttributeBigint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1061,20 +1069,15 @@ def update_big_int_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -1084,15 +1087,19 @@ def update_big_int_attribute( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeBigint) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_boolean_column` instead.") def create_boolean_attribute( self, @@ -1101,11 +1108,10 @@ def create_boolean_attribute( key: str, required: bool, default: Optional[bool] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeBoolean: """ Create a boolean attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_boolean_column` instead. @@ -1123,12 +1129,11 @@ def create_boolean_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeBoolean API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1139,19 +1144,14 @@ def create_boolean_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1159,15 +1159,19 @@ def create_boolean_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeBoolean) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_boolean_column` instead.") def update_boolean_attribute( self, @@ -1176,7 +1180,7 @@ def update_boolean_attribute( key: str, required: bool, default: Optional[bool], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeBoolean: """ Update a boolean attribute. Changing the `default` value will not update already existing documents. @@ -1197,12 +1201,11 @@ def update_boolean_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New attribute key. - Returns ------- AttributeBoolean API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1213,34 +1216,33 @@ def update_boolean_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeBoolean) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_datetime_column` instead.") def create_datetime_attribute( self, @@ -1249,7 +1251,7 @@ def create_datetime_attribute( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeDatetime: """ Create a date time attribute according to the ISO 8601 standard. @@ -1270,12 +1272,11 @@ def create_datetime_attribute( Default value for the attribute in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeDatetime API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1286,19 +1287,14 @@ def create_datetime_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1306,15 +1302,19 @@ def create_datetime_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeDatetime) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_datetime_column` instead.") def update_datetime_attribute( self, @@ -1323,7 +1323,7 @@ def update_datetime_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeDatetime: """ Update a date time attribute. Changing the `default` value will not update already existing documents. @@ -1344,12 +1344,11 @@ def update_datetime_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New attribute key. - Returns ------- AttributeDatetime API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1360,34 +1359,33 @@ def update_datetime_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeDatetime) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_email_column` instead.") def create_email_attribute( self, @@ -1396,11 +1394,10 @@ def create_email_attribute( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeEmail: """ Create an email attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_email_column` instead. @@ -1418,12 +1415,11 @@ def create_email_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeEmail API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1434,19 +1430,14 @@ def create_email_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1454,15 +1445,19 @@ def create_email_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeEmail) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_email_column` instead.") def update_email_attribute( self, @@ -1471,11 +1466,10 @@ def update_email_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeEmail: """ Update an email attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_email_column` instead. @@ -1493,12 +1487,11 @@ def update_email_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeEmail API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1509,34 +1502,33 @@ def update_email_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeEmail) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_enum_column` instead.") def create_enum_attribute( self, @@ -1546,11 +1538,10 @@ def create_enum_attribute( elements: List[str], required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeEnum: """ - Create an enum attribute. The `elements` param acts as a white-list of accepted values for this attribute. - + Create an enum attribute. The `elements` param acts as a white-list of accepted values for this attribute. .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_enum_column` instead. @@ -1570,12 +1561,11 @@ def create_enum_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeEnum API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1586,22 +1576,16 @@ def create_enum_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if elements is None: raise AppwriteException('Missing required parameter: "elements"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) @@ -1610,15 +1594,19 @@ def create_enum_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeEnum) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_enum_column` instead.") def update_enum_attribute( self, @@ -1628,11 +1616,10 @@ def update_enum_attribute( elements: List[str], required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeEnum: """ Update an enum attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_enum_column` instead. @@ -1652,12 +1639,11 @@ def update_enum_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeEnum API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1668,38 +1654,36 @@ def update_enum_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if elements is None: raise AppwriteException('Missing required parameter: "elements"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeEnum) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_float_column` instead.") def create_float_attribute( self, @@ -1710,11 +1694,10 @@ def create_float_attribute( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeFloat: """ Create a float attribute. Optionally, minimum and maximum values can be provided. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_float_column` instead. @@ -1736,12 +1719,11 @@ def create_float_attribute( Default value. Cannot be set when required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeFloat API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1752,19 +1734,14 @@ def create_float_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -1776,15 +1753,19 @@ def create_float_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeFloat) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_float_column` instead.") def update_float_attribute( self, @@ -1795,11 +1776,10 @@ def update_float_attribute( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeFloat: """ Update a float attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_float_column` instead. @@ -1821,12 +1801,11 @@ def update_float_attribute( Maximum value. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeFloat API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1837,20 +1816,15 @@ def update_float_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -1860,15 +1834,19 @@ def update_float_attribute( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeFloat) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_integer_column` instead.") def create_integer_attribute( self, @@ -1879,11 +1857,10 @@ def create_integer_attribute( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeInteger: """ Create an integer attribute. Optionally, minimum and maximum values can be provided. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_integer_column` instead. @@ -1905,12 +1882,11 @@ def create_integer_attribute( Default value. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeInteger API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1921,19 +1897,14 @@ def create_integer_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -1945,15 +1916,19 @@ def create_integer_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeInteger) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_integer_column` instead.") def update_integer_attribute( self, @@ -1964,11 +1939,10 @@ def update_integer_attribute( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeInteger: """ Update an integer attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_integer_column` instead. @@ -1990,12 +1964,11 @@ def update_integer_attribute( Maximum value new_key : Optional[str] New Attribute Key. - Returns ------- AttributeInteger API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2006,20 +1979,15 @@ def update_integer_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -2029,15 +1997,19 @@ def update_integer_attribute( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeInteger) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_ip_column` instead.") def create_ip_attribute( self, @@ -2046,11 +2018,10 @@ def create_ip_attribute( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeIp: """ Create IP address attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_ip_column` instead. @@ -2068,12 +2039,11 @@ def create_ip_attribute( Default value. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeIp API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2084,19 +2054,14 @@ def create_ip_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2104,15 +2069,19 @@ def create_ip_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeIp) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_ip_column` instead.") def update_ip_attribute( self, @@ -2121,11 +2090,10 @@ def update_ip_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeIp: """ Update an ip attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_ip_column` instead. @@ -2143,12 +2111,11 @@ def update_ip_attribute( Default value. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeIp API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2159,34 +2126,33 @@ def update_ip_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeIp) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_line_column` instead.") def create_line_attribute( self, @@ -2194,7 +2160,7 @@ def create_line_attribute( collection_id: str, key: str, required: bool, - default: Optional[List[List[Any]]] = None + default: Optional[List[List[Any]]] = None, ) -> AttributeLine: """ Create a geometric line attribute. @@ -2213,12 +2179,11 @@ def create_line_attribute( Is attribute required? default : Optional[List[List[Any]]] Default value for attribute when not provided, two-dimensional array of coordinate pairs, [[longitude, latitude], [longitude, latitude], …], listing the vertices of the line in order. Cannot be set when attribute is required. - Returns ------- AttributeLine API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2229,33 +2194,32 @@ def create_line_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeLine) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_line_column` instead.") def update_line_attribute( self, @@ -2264,7 +2228,7 @@ def update_line_attribute( key: str, required: bool, default: Optional[List[List[Any]]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeLine: """ Update a line attribute. Changing the `default` value will not update already existing documents. @@ -2285,12 +2249,11 @@ def update_line_attribute( Default value for attribute when not provided, two-dimensional array of coordinate pairs, [[longitude, latitude], [longitude, latitude], …], listing the vertices of the line in order. Cannot be set when attribute is required. new_key : Optional[str] New attribute key. - Returns ------- AttributeLine API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2301,35 +2264,34 @@ def update_line_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeLine) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_longtext_column` instead.") def create_longtext_attribute( self, @@ -2339,11 +2301,10 @@ def create_longtext_attribute( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> AttributeLongtext: """ Create a longtext attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_longtext_column` instead. @@ -2363,12 +2324,11 @@ def create_longtext_attribute( Is attribute an array? encrypt : Optional[bool] Toggle encryption for the attribute. Encryption enhances security by not storing any plain text values in the database. However, encrypted attributes cannot be queried. - Returns ------- AttributeLongtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2379,19 +2339,14 @@ def create_longtext_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2401,15 +2356,19 @@ def create_longtext_attribute( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeLongtext) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_longtext_column` instead.") def update_longtext_attribute( self, @@ -2418,11 +2377,10 @@ def update_longtext_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeLongtext: """ Update a longtext attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_longtext_column` instead. @@ -2440,12 +2398,11 @@ def update_longtext_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeLongtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2456,34 +2413,33 @@ def update_longtext_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeLongtext) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_mediumtext_column` instead.") def create_mediumtext_attribute( self, @@ -2493,11 +2449,10 @@ def create_mediumtext_attribute( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> AttributeMediumtext: """ Create a mediumtext attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_mediumtext_column` instead. @@ -2517,12 +2472,11 @@ def create_mediumtext_attribute( Is attribute an array? encrypt : Optional[bool] Toggle encryption for the attribute. Encryption enhances security by not storing any plain text values in the database. However, encrypted attributes cannot be queried. - Returns ------- AttributeMediumtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2533,19 +2487,14 @@ def create_mediumtext_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2555,15 +2504,19 @@ def create_mediumtext_attribute( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeMediumtext) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_mediumtext_column` instead.") def update_mediumtext_attribute( self, @@ -2572,11 +2525,10 @@ def update_mediumtext_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeMediumtext: """ Update a mediumtext attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_mediumtext_column` instead. @@ -2594,12 +2546,11 @@ def update_mediumtext_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeMediumtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2610,34 +2561,33 @@ def update_mediumtext_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeMediumtext) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_point_column` instead.") def create_point_attribute( self, @@ -2645,7 +2595,7 @@ def create_point_attribute( collection_id: str, key: str, required: bool, - default: Optional[List[float]] = None + default: Optional[List[float]] = None, ) -> AttributePoint: """ Create a geometric point attribute. @@ -2664,12 +2614,11 @@ def create_point_attribute( Is attribute required? default : Optional[List[float]] Default value for attribute when not provided, array of two numbers [longitude, latitude], representing a single coordinate. Cannot be set when attribute is required. - Returns ------- AttributePoint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2680,33 +2629,32 @@ def create_point_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributePoint) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_point_column` instead.") def update_point_attribute( self, @@ -2715,7 +2663,7 @@ def update_point_attribute( key: str, required: bool, default: Optional[List[float]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributePoint: """ Update a point attribute. Changing the `default` value will not update already existing documents. @@ -2736,12 +2684,11 @@ def update_point_attribute( Default value for attribute when not provided, array of two numbers [longitude, latitude], representing a single coordinate. Cannot be set when attribute is required. new_key : Optional[str] New attribute key. - Returns ------- AttributePoint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2752,35 +2699,34 @@ def update_point_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributePoint) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_polygon_column` instead.") def create_polygon_attribute( self, @@ -2788,7 +2734,7 @@ def create_polygon_attribute( collection_id: str, key: str, required: bool, - default: Optional[List[List[Any]]] = None + default: Optional[List[List[Any]]] = None, ) -> AttributePolygon: """ Create a geometric polygon attribute. @@ -2807,12 +2753,11 @@ def create_polygon_attribute( Is attribute required? default : Optional[List[List[Any]]] Default value for attribute when not provided, three-dimensional array where the outer array holds one or more linear rings, [[[longitude, latitude], …], …], the first ring is the exterior boundary, any additional rings are interior holes, and each ring must start and end with the same coordinate pair. Cannot be set when attribute is required. - Returns ------- AttributePolygon API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2823,33 +2768,32 @@ def create_polygon_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributePolygon) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_polygon_column` instead.") def update_polygon_attribute( self, @@ -2858,7 +2802,7 @@ def update_polygon_attribute( key: str, required: bool, default: Optional[List[List[Any]]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributePolygon: """ Update a polygon attribute. Changing the `default` value will not update already existing documents. @@ -2879,12 +2823,11 @@ def update_polygon_attribute( Default value for attribute when not provided, three-dimensional array where the outer array holds one or more linear rings, [[[longitude, latitude], …], …], the first ring is the exterior boundary, any additional rings are interior holes, and each ring must start and end with the same coordinate pair. Cannot be set when attribute is required. new_key : Optional[str] New attribute key. - Returns ------- AttributePolygon API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2895,35 +2838,34 @@ def update_polygon_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributePolygon) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_relationship_column` instead.") def create_relationship_attribute( self, @@ -2934,11 +2876,10 @@ def create_relationship_attribute( two_way: Optional[bool] = None, key: Optional[str] = None, two_way_key: Optional[str] = None, - on_delete: Optional[RelationMutate] = None + on_delete: Optional[RelationMutate] = None, ) -> AttributeRelationship: """ Create relationship attribute. [Learn more about relationship attributes](https://appwrite.io/docs/databases-relationships#relationship-attributes). - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_relationship_column` instead. @@ -2960,12 +2901,11 @@ def create_relationship_attribute( Two Way Attribute Key. on_delete : Optional[RelationMutate] Delete constraint. Possible values are: cascade, restrict, setNull. - Returns ------- AttributeRelationship API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2976,19 +2916,14 @@ def create_relationship_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if related_collection_id is None: raise AppwriteException('Missing required parameter: "related_collection_id"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['relatedCollectionId'] = self._normalize_value(related_collection_id) api_params['type'] = self._normalize_value(type) if two_way is not None: @@ -3000,15 +2935,19 @@ def create_relationship_attribute( if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeRelationship) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_relationship_column` instead.") def update_relationship_attribute( self, @@ -3016,11 +2955,10 @@ def update_relationship_attribute( collection_id: str, key: str, on_delete: Optional[RelationMutate] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeRelationship: """ Update relationship attribute. [Learn more about relationship attributes](https://appwrite.io/docs/databases-relationships#relationship-attributes). - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_relationship_column` instead. @@ -3036,12 +2974,11 @@ def update_relationship_attribute( Delete constraint. Possible values are: cascade, restrict, setNull. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeRelationship API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3052,31 +2989,31 @@ def update_relationship_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeRelationship) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_string_column` instead.") def create_string_attribute( self, @@ -3087,11 +3024,10 @@ def create_string_attribute( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> AttributeString: """ Create a string attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_string_column` instead. @@ -3113,12 +3049,11 @@ def create_string_attribute( Is attribute an array? encrypt : Optional[bool] Toggle encryption for the attribute. Encryption enhances security by not storing any plain text values in the database. However, encrypted attributes cannot be queried. - Returns ------- AttributeString API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3129,22 +3064,16 @@ def create_string_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if size is None: raise AppwriteException('Missing required parameter: "size"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) @@ -3155,15 +3084,19 @@ def create_string_attribute( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeString) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_string_column` instead.") def update_string_attribute( self, @@ -3173,11 +3106,10 @@ def update_string_attribute( required: bool, default: Optional[str], size: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeString: """ Update a string attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_string_column` instead. @@ -3197,12 +3129,11 @@ def update_string_attribute( Maximum size of the string attribute. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeString API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3213,20 +3144,15 @@ def update_string_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if size is not None: @@ -3234,15 +3160,19 @@ def update_string_attribute( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeString) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_text_column` instead.") def create_text_attribute( self, @@ -3252,11 +3182,10 @@ def create_text_attribute( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> AttributeText: """ Create a text attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_text_column` instead. @@ -3276,12 +3205,11 @@ def create_text_attribute( Is attribute an array? encrypt : Optional[bool] Toggle encryption for the attribute. Encryption enhances security by not storing any plain text values in the database. However, encrypted attributes cannot be queried. - Returns ------- AttributeText API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3292,19 +3220,14 @@ def create_text_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -3314,15 +3237,19 @@ def create_text_attribute( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeText) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_text_column` instead.") def update_text_attribute( self, @@ -3331,11 +3258,10 @@ def update_text_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeText: """ Update a text attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_text_column` instead. @@ -3353,12 +3279,11 @@ def update_text_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeText API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3369,34 +3294,33 @@ def update_text_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeText) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_url_column` instead.") def create_url_attribute( self, @@ -3405,11 +3329,10 @@ def create_url_attribute( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> AttributeUrl: """ Create a URL attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_url_column` instead. @@ -3427,12 +3350,11 @@ def create_url_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. array : Optional[bool] Is attribute an array? - Returns ------- AttributeUrl API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3443,19 +3365,14 @@ def create_url_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -3463,15 +3380,19 @@ def create_url_attribute( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeUrl) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_url_column` instead.") def update_url_attribute( self, @@ -3480,11 +3401,10 @@ def update_url_attribute( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeUrl: """ Update an url attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_url_column` instead. @@ -3502,12 +3422,11 @@ def update_url_attribute( Default value for attribute when not provided. Cannot be set when attribute is required. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeUrl API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3518,34 +3437,33 @@ def update_url_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeUrl) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_varchar_column` instead.") def create_varchar_attribute( self, @@ -3556,11 +3474,10 @@ def create_varchar_attribute( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> AttributeVarchar: """ Create a varchar attribute. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.create_varchar_column` instead. @@ -3582,12 +3499,11 @@ def create_varchar_attribute( Is attribute an array? encrypt : Optional[bool] Toggle encryption for the attribute. Encryption enhances security by not storing any plain text values in the database. However, encrypted attributes cannot be queried. - Returns ------- AttributeVarchar API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3598,22 +3514,16 @@ def create_varchar_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if size is None: raise AppwriteException('Missing required parameter: "size"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) @@ -3624,15 +3534,19 @@ def create_varchar_attribute( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeVarchar) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_varchar_column` instead.") def update_varchar_attribute( self, @@ -3642,11 +3556,10 @@ def update_varchar_attribute( required: bool, default: Optional[str], size: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> AttributeVarchar: """ Update a varchar attribute. Changing the `default` value will not update already existing documents. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_varchar_column` instead. @@ -3666,12 +3579,11 @@ def update_varchar_attribute( Maximum size of the varchar attribute. new_key : Optional[str] New Attribute Key. - Returns ------- AttributeVarchar API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3682,20 +3594,15 @@ def update_varchar_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if size is not None: @@ -3703,22 +3610,37 @@ def update_varchar_attribute( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AttributeVarchar) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get_column` instead.") def get_attribute( self, database_id: str, collection_id: str, - key: str - ) -> Union[AttributeBoolean, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributeString]: + key: str, + ) -> Union[ + AttributeBoolean, + AttributeInteger, + AttributeFloat, + AttributeEmail, + AttributeEnum, + AttributeUrl, + AttributeIp, + AttributeDatetime, + AttributeRelationship, + AttributeString, + ]: """ Get attribute by ID. @@ -3732,12 +3654,11 @@ def get_attribute( Collection ID. key : str Attribute Key. - Returns ------- Union[AttributeBoolean, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributeString] API response as one of the typed response models - + Raises ------ AppwriteException @@ -3748,22 +3669,23 @@ def get_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) if not isinstance(response, dict): raise AppwriteException('Expected object response when hydrating a response model') @@ -3799,13 +3721,12 @@ def get_attribute( raise AppwriteException('Unable to match response to any known model') - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_column` instead.") def delete_attribute( self, database_id: str, collection_id: str, - key: str + key: str, ) -> Dict[str, Any]: """ Deletes an attribute. @@ -3820,12 +3741,11 @@ def delete_attribute( Collection ID. key : str Attribute Key. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -3836,26 +3756,26 @@ def delete_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.list_rows` instead.") def list_documents( self, @@ -3865,7 +3785,7 @@ def list_documents( transaction_id: Optional[str] = None, total: Optional[bool] = None, ttl: Optional[float] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> DocumentList[T]: """ Get a list of all the user's documents in a given collection. You can use the query params to filter your results. @@ -3886,15 +3806,14 @@ def list_documents( When set to false, the total count returned will be 0 and will not be calculated. ttl : Optional[float] TTL (seconds) for caching list responses. Responses are stored in an in-memory key-value cache, keyed per project, collection, schema version (attributes and indexes), caller authorization roles, and the exact query — so users with different permissions never share cached entries. Schema changes invalidate cached entries automatically; document writes do not, so choose a TTL you are comfortable serving as stale data. Set to 0 to disable caching. Must be between 0 and 86400 (24 hours). - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- DocumentList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3905,13 +3824,10 @@ def list_documents( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: @@ -3921,14 +3837,18 @@ def list_documents( if ttl is not None: api_params['ttl'] = self._normalize_value(ttl) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return DocumentList.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_row` instead.") def create_document( self, @@ -3938,7 +3858,7 @@ def create_document( data: Dict[str, Any], permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Create a new Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection) API or directly from your database console. @@ -3959,15 +3879,14 @@ def create_document( An array of permissions strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3978,19 +3897,14 @@ def create_document( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - if data is None: raise AppwriteException('Missing required parameter: "data"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['documentId'] = self._normalize_value(document_id) api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -3998,15 +3912,19 @@ def create_document( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_rows` instead.") def create_documents( self, @@ -4014,7 +3932,7 @@ def create_documents( collection_id: str, documents: List[Dict[str, Any]], transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> DocumentList[T]: """ Create new Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection) API or directly from your database console. @@ -4031,15 +3949,14 @@ def create_documents( Array of documents data as JSON objects. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- DocumentList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4050,29 +3967,29 @@ def create_documents( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if documents is None: raise AppwriteException('Missing required parameter: "documents"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['documents'] = self._normalize_value(documents) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return DocumentList.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.upsert_rows` instead.") def upsert_documents( self, @@ -4080,11 +3997,10 @@ def upsert_documents( collection_id: str, documents: List[Dict[str, Any]], transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> DocumentList[T]: """ Create or update Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection) API or directly from your database console. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.upsert_rows` instead. @@ -4098,15 +4014,14 @@ def upsert_documents( Array of document data as JSON objects. May contain partial documents. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- DocumentList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4117,29 +4032,29 @@ def upsert_documents( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if documents is None: raise AppwriteException('Missing required parameter: "documents"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['documents'] = self._normalize_value(documents) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return DocumentList.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_rows` instead.") def update_documents( self, @@ -4148,7 +4063,7 @@ def update_documents( data: Optional[Dict[str, Any]] = None, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> DocumentList[T]: """ Update all documents that match your queries, if no queries are submitted then all documents are updated. You can pass only specific fields to be updated. @@ -4167,15 +4082,14 @@ def update_documents( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- DocumentList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4186,13 +4100,10 @@ def update_documents( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if queries is not None: @@ -4200,15 +4111,19 @@ def update_documents( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return DocumentList.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_rows` instead.") def delete_documents( self, @@ -4216,7 +4131,7 @@ def delete_documents( collection_id: str, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> DocumentList[T]: """ Bulk delete documents using queries, if no queries are passed then all documents are deleted. @@ -4233,15 +4148,14 @@ def delete_documents( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- DocumentList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4252,27 +4166,28 @@ def delete_documents( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return DocumentList.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get_row` instead.") def get_document( self, @@ -4281,7 +4196,7 @@ def get_document( document_id: str, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Get a document by its unique ID. This endpoint response returns a JSON object with the document data. @@ -4300,15 +4215,14 @@ def get_document( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID to read uncommitted changes within the transaction. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4319,30 +4233,30 @@ def get_document( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.upsert_row` instead.") def upsert_document( self, @@ -4352,7 +4266,7 @@ def upsert_document( data: Optional[Dict[str, Any]] = None, permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Create or update a Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection) API or directly from your database console. @@ -4373,15 +4287,14 @@ def upsert_document( An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4392,17 +4305,13 @@ def upsert_document( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -4410,15 +4319,19 @@ def upsert_document( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_row` instead.") def update_document( self, @@ -4428,7 +4341,7 @@ def update_document( data: Optional[Dict[str, Any]] = None, permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Update a document by its unique ID. Using the patch method you can pass only specific fields that will get updated. @@ -4449,15 +4362,14 @@ def update_document( An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4468,17 +4380,13 @@ def update_document( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -4486,22 +4394,26 @@ def update_document( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_row` instead.") def delete_document( self, database_id: str, collection_id: str, document_id: str, - transaction_id: Optional[str] = None + transaction_id: Optional[str] = None, ) -> Dict[str, Any]: """ Delete a document by its unique ID. @@ -4518,12 +4430,11 @@ def delete_document( Document ID. transaction_id : Optional[str] Transaction ID for staging the operation. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -4534,28 +4445,28 @@ def delete_document( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) - if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.decrement_row_column` instead.") def decrement_document_attribute( self, @@ -4566,7 +4477,7 @@ def decrement_document_attribute( value: Optional[float] = None, min: Optional[float] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Decrement a specific attribute of a document by a given value. @@ -4589,15 +4500,14 @@ def decrement_document_attribute( Minimum value for the attribute. If the current value is lesser than this value, an exception will be thrown. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4608,21 +4518,16 @@ def decrement_document_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - if attribute is None: raise AppwriteException('Missing required parameter: "attribute"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) api_path = api_path.replace('{attribute}', str(self._normalize_value(attribute))) - if value is not None: api_params['value'] = self._normalize_value(value) if min is not None: @@ -4630,15 +4535,19 @@ def decrement_document_attribute( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.increment_row_column` instead.") def increment_document_attribute( self, @@ -4649,7 +4558,7 @@ def increment_document_attribute( value: Optional[float] = None, max: Optional[float] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Document[T]: """ Increment a specific attribute of a document by a given value. @@ -4672,15 +4581,14 @@ def increment_document_attribute( Maximum value for the attribute. If the current value is greater than this value, an error will be thrown. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Document[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4691,21 +4599,16 @@ def increment_document_attribute( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if document_id is None: raise AppwriteException('Missing required parameter: "document_id"') - if attribute is None: raise AppwriteException('Missing required parameter: "attribute"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) api_path = api_path.replace('{attribute}', str(self._normalize_value(attribute))) - if value is not None: api_params['value'] = self._normalize_value(value) if max is not None: @@ -4713,22 +4616,26 @@ def increment_document_attribute( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Document.with_data(response, model_type) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.list_indexes` instead.") def list_indexes( self, database_id: str, collection_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> IndexList: """ List indexes in the collection. @@ -4745,12 +4652,11 @@ def list_indexes( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, type, status, attributes, error total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- IndexList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4761,26 +4667,27 @@ def list_indexes( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=IndexList) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.create_index` instead.") def create_index( self, @@ -4790,7 +4697,7 @@ def create_index( type: DatabasesIndexType, attributes: List[str], orders: Optional[List[OrderBy]] = None, - lengths: Optional[List[float]] = None + lengths: Optional[List[float]] = None, ) -> Index: """ Creates an index on the attributes listed. Your index should include all the attributes you will query in a single request. @@ -4814,12 +4721,11 @@ def create_index( Array of index orders. Maximum of 100 orders are allowed. lengths : Optional[List[float]] Length of index. Maximum of 100 - Returns ------- Index API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4830,22 +4736,16 @@ def create_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if attributes is None: raise AppwriteException('Missing required parameter: "attributes"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) - api_params['key'] = self._normalize_value(key) api_params['type'] = self._normalize_value(type) api_params['attributes'] = self._normalize_value(attributes) @@ -4854,21 +4754,25 @@ def create_index( if lengths is not None: api_params['lengths'] = self._normalize_value(lengths) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Index) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.get_index` instead.") def get_index( self, database_id: str, collection_id: str, - key: str + key: str, ) -> Index: """ Get an index by its unique ID. @@ -4883,12 +4787,11 @@ def get_index( Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). key : str Index Key. - Returns ------- Index API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4899,32 +4802,32 @@ def get_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Index) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.delete_index` instead.") def delete_index( self, database_id: str, collection_id: str, - key: str + key: str, ) -> Dict[str, Any]: """ Delete an index. @@ -4939,12 +4842,11 @@ def delete_index( Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). key : str Index Key. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -4955,22 +4857,22 @@ def delete_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if collection_id is None: raise AppwriteException('Missing required parameter: "collection_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/documents_db.py b/appwrite/services/documents_db.py new file mode 100644 index 00000000..d136fa34 --- /dev/null +++ b/appwrite/services/documents_db.py @@ -0,0 +1,2097 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union, Type, TypeVar +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..models.database_list import DatabaseList +from ..models.database import Database +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from ..models.transaction_list import TransactionList +from ..models.transaction import Transaction +from ..models.collection_list import CollectionList +from ..models.collection import Collection +from ..models.document_list import DocumentList +from ..models.document import Document +from ..models.index_list import IndexList +from ..enums.documents_db_index_type import DocumentsDBIndexType +from ..enums.order_by import OrderBy +from ..models.index import Index +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.database_status import DatabaseStatus + +T = TypeVar('T') + + +class DocumentsDB(Service): + + def __init__(self, client) -> None: + super(DocumentsDB, self).__init__(client) + + def list( + self, + queries: Optional[List[str]] = None, + total: Optional[bool] = None, + ) -> DatabaseList: + """ + Get a list of all databases from the current Appwrite project. You can use the search parameter to filter your results. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following columns: name + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + DatabaseList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseList) + + def create( + self, + database_id: str, + name: str, + enabled: Optional[bool] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + ) -> Database: + """ + Create a new Database. + + Parameters + ---------- + database_id : str + Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Database name. Max length: 128 chars. + enabled : Optional[bool] + Is the database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + specification : Optional[str] + Database specification. Defaults to `serverless`, which creates the database on the shared pool. Any other value provisions a dedicated database on that specification. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Requires a dedicated `specification`; must be 0 for a serverless database. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Requires a dedicated `specification`; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_params['databaseId'] = self._normalize_value(database_id) + api_params['name'] = self._normalize_value(name) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def list_specifications( + self, + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/specifications' + api_params = {} + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def list_transactions( + self, + queries: Optional[List[str]] = None, + ) -> TransactionList: + """ + List transactions across all databases. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). + Returns + ------- + TransactionList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=TransactionList) + + def create_transaction( + self, + ttl: Optional[float] = None, + ) -> Transaction: + """ + Create a new transaction. + + Parameters + ---------- + ttl : Optional[float] + Seconds before the transaction expires. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions' + api_params = {} + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def get_transaction( + self, + transaction_id: str, + ) -> Transaction: + """ + Get a transaction by its unique ID. + + Parameters + ---------- + transaction_id : str + Transaction ID. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def update_transaction( + self, + transaction_id: str, + commit: Optional[bool] = None, + rollback: Optional[bool] = None, + ) -> Transaction: + """ + Update a transaction, to either commit or roll back its operations. + + Parameters + ---------- + transaction_id : str + Transaction ID. + commit : Optional[bool] + Commit transaction? + rollback : Optional[bool] + Rollback transaction? + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + if commit is not None: + api_params['commit'] = self._normalize_value(commit) + if rollback is not None: + api_params['rollback'] = self._normalize_value(rollback) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def delete_transaction( + self, + transaction_id: str, + ) -> Dict[str, Any]: + """ + Delete a transaction by its unique ID. + + Parameters + ---------- + transaction_id : str + Transaction ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def create_operations( + self, + transaction_id: str, + operations: Optional[List[Dict[str, Any]]] = None, + ) -> Transaction: + """ + Create multiple operations in a single transaction. + + Parameters + ---------- + transaction_id : str + Transaction ID. + operations : Optional[List[Dict[str, Any]]] + Array of staged operations. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/transactions/{transactionId}/operations' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + if operations is not None: + api_params['operations'] = self._normalize_value(operations) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def get( + self, + database_id: str, + ) -> Database: + """ + Get a database by its unique ID. This endpoint response returns a JSON object with the database metadata. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def update( + self, + database_id: str, + name: str, + enabled: Optional[bool] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + ) -> Database: + """ + Update a database by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + name : str + Database name. Max length: 128 chars. + enabled : Optional[bool] + Is database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + specification : Optional[str] + Database specification. Resizing between dedicated specifications changes cpu, memory, storage and the connection ceiling via a rolling cutover with zero downtime. Moving a `serverless` database onto a dedicated specification is a data migration, not a resize. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['name'] = self._normalize_value(name) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def delete( + self, + database_id: str, + ) -> Dict[str, Any]: + """ + Delete a database by its unique ID. Only API keys with with databases.write scope can delete a database. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def list_collections( + self, + database_id: str, + queries: Optional[List[str]] = None, + search: Optional[str] = None, + total: Optional[bool] = None, + ) -> CollectionList: + """ + Get a list of all collections that belong to the provided databaseId. You can use the search parameter to filter your results. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, enabled, documentSecurity + search : Optional[str] + Search term to filter your list results. Max length: 256 chars. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + CollectionList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if search is not None: + api_params['search'] = self._normalize_value(search) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=CollectionList) + + def create_collection( + self, + database_id: str, + collection_id: str, + name: str, + permissions: Optional[List[str]] = None, + document_security: Optional[bool] = None, + enabled: Optional[bool] = None, + attributes: Optional[List[Dict[str, Any]]] = None, + indexes: Optional[List[Dict[str, Any]]] = None, + ) -> Collection: + """ + Create a new Collection. Before using this route, you should create a new database resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Collection name. Max length: 128 chars. + permissions : Optional[List[str]] + An array of permissions strings. By default, no user is granted with any permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + document_security : Optional[bool] + Enables configuring permissions for individual documents. A user needs one of document or collection level permissions to access a document. [Learn more about permissions](https://appwrite.io/docs/permissions). + enabled : Optional[bool] + Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. + attributes : Optional[List[Dict[str, Any]]] + Array of attribute definitions to create. Each attribute should contain: key (string), type (string: string, varchar, text, mediumtext, longtext, integer, bigint, double, boolean, datetime, point, linestring, polygon, email, url, ip, enum), size (integer, required for string and varchar types), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. + indexes : Optional[List[Dict[str, Any]]] + Array of index definitions to create. Each index should contain: key (string), type (string: key, fulltext, unique, spatial), attributes (array of attribute keys), orders (array of ASC/DESC, optional), and lengths (array of integers, optional). + Returns + ------- + Collection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['collectionId'] = self._normalize_value(collection_id) + api_params['name'] = self._normalize_value(name) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if document_security is not None: + api_params['documentSecurity'] = self._normalize_value(document_security) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if attributes is not None: + api_params['attributes'] = self._normalize_value(attributes) + if indexes is not None: + api_params['indexes'] = self._normalize_value(indexes) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Collection) + + def get_collection( + self, + database_id: str, + collection_id: str, + ) -> Collection: + """ + Get a collection by its unique ID. This endpoint response returns a JSON object with the collection metadata. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + Returns + ------- + Collection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Collection) + + def update_collection( + self, + database_id: str, + collection_id: str, + name: str, + permissions: Optional[List[str]] = None, + document_security: Optional[bool] = None, + enabled: Optional[bool] = None, + purge: Optional[bool] = None, + ) -> Collection: + """ + Update a collection by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + name : str + Collection name. Max length: 128 chars. + permissions : Optional[List[str]] + An array of permission strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + document_security : Optional[bool] + Enables configuring permissions for individual documents. A user needs one of document or collection level permissions to access a document. [Learn more about permissions](https://appwrite.io/docs/permissions). + enabled : Optional[bool] + Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. + purge : Optional[bool] + When true, purge all cached list responses for this collection as part of the update. Use this to force readers to see fresh data immediately instead of waiting for the cache TTL to expire. + Returns + ------- + Collection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['name'] = self._normalize_value(name) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if document_security is not None: + api_params['documentSecurity'] = self._normalize_value(document_security) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if purge is not None: + api_params['purge'] = self._normalize_value(purge) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Collection) + + def delete_collection( + self, + database_id: str, + collection_id: str, + ) -> Dict[str, Any]: + """ + Delete a collection by its unique ID. Only users with write permissions have access to delete this resource. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def list_documents( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + total: Optional[bool] = None, + ttl: Optional[float] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Get a list of all the user's documents in a given collection. You can use the query params to filter your results. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID to read uncommitted changes within the transaction. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + ttl : Optional[float] + TTL (seconds) for cached responses when caching is enabled for select queries. Must be between 0 and 86400 (24 hours). + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + if total is not None: + api_params['total'] = self._normalize_value(total) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def create_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Dict[str, Any], + permissions: Optional[List[str]] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Create a new Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). Make sure to define attributes before creating documents. + document_id : str + Document ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + data : Dict[str, Any] + Document data as JSON object. + permissions : Optional[List[str]] + An array of permissions strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + if data is None: + raise AppwriteException('Missing required parameter: "data"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documentId'] = self._normalize_value(document_id) + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def create_documents( + self, + database_id: str, + collection_id: str, + documents: List[Dict[str, Any]], + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Create new Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). Make sure to define attributes before creating documents. + documents : List[Dict[str, Any]] + Array of documents data as JSON objects. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if documents is None: + raise AppwriteException('Missing required parameter: "documents"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documents'] = self._normalize_value(documents) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def upsert_documents( + self, + database_id: str, + collection_id: str, + documents: List[Dict[str, Any]], + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Create or update Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + documents : List[Dict[str, Any]] + Array of document data as JSON objects. May contain partial documents. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if documents is None: + raise AppwriteException('Missing required parameter: "documents"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documents'] = self._normalize_value(documents) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def update_documents( + self, + database_id: str, + collection_id: str, + data: Optional[Dict[str, Any]] = None, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Update all documents that match your queries, if no queries are submitted then all documents are updated. You can pass only specific fields to be updated. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include only attribute and value pairs to be updated. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def delete_documents( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Bulk delete documents using queries, if no queries are passed then all documents are deleted. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def get_document( + self, + database_id: str, + collection_id: str, + document_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Get a document by its unique ID. This endpoint response returns a JSON object with the document data. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + document_id : str + Document ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID to read uncommitted changes within the transaction. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def upsert_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Optional[Dict[str, Any]] = None, + permissions: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Create or update a Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include all required fields of the document to be created or updated. + permissions : Optional[List[str]] + An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def update_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Optional[Dict[str, Any]] = None, + permissions: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Update a document by its unique ID. Using the patch method you can pass only specific fields that will get updated. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include only fields and value pairs to be updated. + permissions : Optional[List[str]] + An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def delete_document( + self, + database_id: str, + collection_id: str, + document_id: str, + transaction_id: Optional[str] = None, + ) -> Dict[str, Any]: + """ + Delete a document by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + document_id : str + Document ID. + transaction_id : Optional[str] + Transaction ID for staging the operation. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def decrement_document_attribute( + self, + database_id: str, + collection_id: str, + document_id: str, + attribute: str, + value: Optional[float] = None, + min: Optional[float] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Decrement a specific column of a row by a given value. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + attribute : str + Attribute key. + value : Optional[float] + Value to decrement the attribute by. The value must be a number. + min : Optional[float] + Minimum value for the attribute. If the current value is lesser than this value, an exception will be thrown. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}/{attribute}/decrement' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + if attribute is None: + raise AppwriteException('Missing required parameter: "attribute"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + api_path = api_path.replace('{attribute}', str(self._normalize_value(attribute))) + if value is not None: + api_params['value'] = self._normalize_value(value) + if min is not None: + api_params['min'] = self._normalize_value(min) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def increment_document_attribute( + self, + database_id: str, + collection_id: str, + document_id: str, + attribute: str, + value: Optional[float] = None, + max: Optional[float] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Increment a specific column of a row by a given value. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + attribute : str + Attribute key. + value : Optional[float] + Value to increment the attribute by. The value must be a number. + max : Optional[float] + Maximum value for the attribute. If the current value is greater than this value, an error will be thrown. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/documents/{documentId}/{attribute}/increment' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + if attribute is None: + raise AppwriteException('Missing required parameter: "attribute"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + api_path = api_path.replace('{attribute}', str(self._normalize_value(attribute))) + if value is not None: + api_params['value'] = self._normalize_value(value) + if max is not None: + api_params['max'] = self._normalize_value(max) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def list_indexes( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None, + ) -> IndexList: + """ + List indexes in the collection. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, type, status, attributes, error + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + IndexList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/indexes' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=IndexList) + + def create_index( + self, + database_id: str, + collection_id: str, + key: str, + type: DocumentsDBIndexType, + attributes: List[str], + orders: Optional[List[OrderBy]] = None, + lengths: Optional[List[float]] = None, + ) -> Index: + """ + Creates an index on the attributes listed. Your index should include all the attributes you will query in a single request. + Attributes can be `key`, `fulltext`, and `unique`. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + type : DocumentsDBIndexType + Index type. + attributes : List[str] + Array of attributes to index. Maximum of 100 attributes are allowed, each 32 characters long. + orders : Optional[List[OrderBy]] + Array of index orders. Maximum of 100 orders are allowed. + lengths : Optional[List[float]] + Length of index. Maximum of 100 + Returns + ------- + Index + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/indexes' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + if type is None: + raise AppwriteException('Missing required parameter: "type"') + if attributes is None: + raise AppwriteException('Missing required parameter: "attributes"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['key'] = self._normalize_value(key) + api_params['type'] = self._normalize_value(type) + api_params['attributes'] = self._normalize_value(attributes) + if orders is not None: + api_params['orders'] = self._normalize_value(orders) + if lengths is not None: + api_params['lengths'] = self._normalize_value(lengths) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Index) + + def get_index( + self, + database_id: str, + collection_id: str, + key: str, + ) -> Index: + """ + Get index by ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + Returns + ------- + Index + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/indexes/{key}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{key}', str(self._normalize_value(key))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Index) + + def delete_index( + self, + database_id: str, + collection_id: str, + key: str, + ) -> Dict[str, Any]: + """ + Delete an index. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/collections/{collectionId}/indexes/{key}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{key}', str(self._normalize_value(key))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_replicas( + self, + database_id: str, + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + def get_status( + self, + database_id: str, + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/documentsdb/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseStatus) diff --git a/appwrite/services/embeddings.py b/appwrite/services/embeddings.py index 50848d06..4068b552 100644 --- a/appwrite/services/embeddings.py +++ b/appwrite/services/embeddings.py @@ -6,6 +6,7 @@ from ..enums.embedding_model import EmbeddingModel from ..models.embedding_list import EmbeddingList + class Embeddings(Service): def __init__(self, client) -> None: @@ -14,11 +15,10 @@ def __init__(self, client) -> None: def create_text_embeddings( self, texts: List[str], - model: Optional[EmbeddingModel] = None + model: Optional[EmbeddingModel] = None, ) -> EmbeddingList: """ Generate vector embeddings for an array of text using the selected embedding model. Use the returned vectors to power semantic search and similarity queries against your vector collections. - Parameters ---------- @@ -26,12 +26,11 @@ def create_text_embeddings( Array of text to generate embeddings. model : Optional[EmbeddingModel] The embedding model to use for generating vector embeddings. - Returns ------- EmbeddingList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -42,17 +41,19 @@ def create_text_embeddings( api_params = {} if texts is None: raise AppwriteException('Missing required parameter: "texts"') - - api_params['texts'] = self._normalize_value(texts) if model is not None: api_params['model'] = self._normalize_value(model) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=EmbeddingList) - diff --git a/appwrite/services/functions.py b/appwrite/services/functions.py index 07bd41b4..594c0f6b 100644 --- a/appwrite/services/functions.py +++ b/appwrite/services/functions.py @@ -21,6 +21,7 @@ from ..models.variable_list import VariableList from ..models.variable import Variable + class Functions(Service): def __init__(self, client) -> None: @@ -30,7 +31,7 @@ def list( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> FunctionList: """ Get a list of all the project's functions. You can use the query params to filter your results. @@ -43,12 +44,11 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- FunctionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -57,7 +57,6 @@ def list( api_path = '/functions' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -65,14 +64,18 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=FunctionList) - def create( self, function_id: str, @@ -96,7 +99,7 @@ def create( provider_paths: Optional[List[str]] = None, build_specification: Optional[str] = None, runtime_specification: Optional[str] = None, - deployment_retention: Optional[float] = None + deployment_retention: Optional[float] = None, ) -> Function: """ Create a new function. You can pass a list of [permissions](https://appwrite.io/docs/permissions) to allow different project users or team with access to execute the function using the client API. @@ -147,12 +150,11 @@ def create( Runtime specification for the function executions. deployment_retention : Optional[float] Days to keep non-active deployments before deletion. Value 0 means all deployments will be kept. - Returns ------- Function API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -163,14 +165,10 @@ def create( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if runtime is None: raise AppwriteException('Missing required parameter: "runtime"') - - api_params['functionId'] = self._normalize_value(function_id) api_params['name'] = self._normalize_value(name) api_params['runtime'] = self._normalize_value(runtime) @@ -213,26 +211,29 @@ def create( if deployment_retention is not None: api_params['deploymentRetention'] = self._normalize_value(deployment_retention) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Function) - def list_runtimes( - self + self, ) -> RuntimeList: """ Get a list of all runtimes that are currently active on your instance. - Returns ------- RuntimeList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -242,17 +243,21 @@ def list_runtimes( api_path = '/functions/runtimes' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=RuntimeList) - def list_specifications( self, - type: Optional[str] = None + type: Optional[str] = None, ) -> SpecificationList: """ List allowed function specifications for this instance. @@ -261,12 +266,11 @@ def list_specifications( ---------- type : Optional[str] Specification type to list. Can be one of: runtimes, builds. Defaults to runtimes. - Returns ------- SpecificationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -275,21 +279,24 @@ def list_specifications( api_path = '/functions/specifications' api_params = {} - if type is not None: api_params['type'] = self._normalize_value(type) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SpecificationList) - def get( self, - function_id: str + function_id: str, ) -> Function: """ Get a function by its unique ID. @@ -298,12 +305,11 @@ def get( ---------- function_id : str Function ID. - Returns ------- Function API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -314,18 +320,20 @@ def get( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Function) - def update( self, function_id: str, @@ -349,7 +357,7 @@ def update( provider_paths: Optional[List[str]] = None, build_specification: Optional[str] = None, runtime_specification: Optional[str] = None, - deployment_retention: Optional[float] = None + deployment_retention: Optional[float] = None, ) -> Function: """ Update function by its unique ID. @@ -400,12 +408,11 @@ def update( Runtime specification for the function executions. deployment_retention : Optional[float] Days to keep non-active deployments before deletion. Value 0 means all deployments will be kept. - Returns ------- Function API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -416,12 +423,9 @@ def update( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['name'] = self._normalize_value(name) if runtime is not None: api_params['runtime'] = self._normalize_value(runtime) @@ -464,18 +468,22 @@ def update( if deployment_retention is not None: api_params['deploymentRetention'] = self._normalize_value(deployment_retention) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Function) - def delete( self, - function_id: str + function_id: str, ) -> Dict[str, Any]: """ Delete a function by its unique ID. @@ -484,12 +492,11 @@ def delete( ---------- function_id : str Function ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -500,22 +507,24 @@ def delete( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_function_deployment( self, function_id: str, - deployment_id: str + deployment_id: str, ) -> Function: """ Update the function active deployment. Use this endpoint to switch the code deployment that should be used when visitor opens your function. @@ -526,12 +535,11 @@ def update_function_deployment( Function ID. deployment_id : str Deployment ID. - Returns ------- Function API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -542,29 +550,30 @@ def update_function_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['deploymentId'] = self._normalize_value(deployment_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Function) - def list_deployments( self, function_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> DeploymentList: """ Get a list of all the function's code deployments. You can use the query params to filter your results. @@ -579,12 +588,11 @@ def list_deployments( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- DeploymentList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -595,9 +603,7 @@ def list_deployments( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -605,14 +611,18 @@ def list_deployments( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DeploymentList) - def create_deployment( self, function_id: str, @@ -620,13 +630,13 @@ def create_deployment( activate: bool, entrypoint: Optional[str] = None, commands: Optional[str] = None, - on_progress = None + on_progress=None, ) -> Deployment: """ Create a new function code deployment. Use this endpoint to upload a new version of your code function. To execute your newly uploaded code, you'll need to update the function's deployment to use your new deployment UID. - + This endpoint accepts a tar.gz file compressed with your code. Make sure to include any dependencies your code has within the compressed file. You can learn more about code packaging in the [Appwrite Cloud Functions tutorial](https://appwrite.io/docs/functions). - + Use the "command" param to set the entrypoint used to execute your code. Parameters @@ -641,14 +651,14 @@ def create_deployment( Entrypoint File. commands : Optional[str] Build Commands. - on_progress : callable, optional + on_progress : callable, optional Optional callback for upload progress - + Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -659,15 +669,11 @@ def create_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if code is None: raise AppwriteException('Missing required parameter: "code"') - if activate is None: raise AppwriteException('Missing required parameter: "activate"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - if entrypoint is not None: api_params['entrypoint'] = self._normalize_value(entrypoint) if commands is not None: @@ -677,23 +683,28 @@ def create_deployment( param_name = 'code' - upload_id = '' - response = self.client.chunked_upload(api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'multipart/form-data', - 'accept': 'application/json', - }, api_params, param_name, on_progress, upload_id) + response = self.client.chunked_upload( + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'multipart/form-data', + 'accept': 'application/json', + }, + api_params, + param_name, + on_progress, + upload_id, + ) return self._parse_response(response, model=Deployment) - def create_duplicate_deployment( self, function_id: str, deployment_id: str, - build_id: Optional[str] = None + build_id: Optional[str] = None, ) -> Deployment: """ Create a new build for an existing function deployment. This endpoint allows you to rebuild a deployment with the updated function configuration, including its entrypoint and build commands if they have been modified. The build process will be queued and executed asynchronously. The original deployment's code will be preserved and used for the new build. @@ -706,12 +717,11 @@ def create_duplicate_deployment( Deployment ID. build_id : Optional[str] Build unique ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -722,25 +732,26 @@ def create_duplicate_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['deploymentId'] = self._normalize_value(deployment_id) if build_id is not None: api_params['buildId'] = self._normalize_value(build_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def create_template_deployment( self, function_id: str, @@ -749,11 +760,11 @@ def create_template_deployment( root_directory: str, type: TemplateReferenceType, reference: str, - activate: Optional[bool] = None + activate: Optional[bool] = None, ) -> Deployment: """ Create a deployment based on a template. - + Use this endpoint with combination of [listTemplates](https://appwrite.io/docs/products/functions/templates) to find the template details. Parameters @@ -772,12 +783,11 @@ def create_template_deployment( Reference value, can be a commit hash, branch name, or release tag activate : Optional[bool] Automatically activate the deployment when it is finished building. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -788,24 +798,17 @@ def create_template_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if repository is None: raise AppwriteException('Missing required parameter: "repository"') - if owner is None: raise AppwriteException('Missing required parameter: "owner"') - if root_directory is None: raise AppwriteException('Missing required parameter: "root_directory"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if reference is None: raise AppwriteException('Missing required parameter: "reference"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['repository'] = self._normalize_value(repository) api_params['owner'] = self._normalize_value(owner) api_params['rootDirectory'] = self._normalize_value(root_directory) @@ -814,25 +817,29 @@ def create_template_deployment( if activate is not None: api_params['activate'] = self._normalize_value(activate) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def create_vcs_deployment( self, function_id: str, type: VCSReferenceType, reference: str, - activate: Optional[bool] = None + activate: Optional[bool] = None, ) -> Deployment: """ Create a deployment when a function is connected to VCS. - + This endpoint lets you create deployment from a branch, commit, or a tag. Parameters @@ -845,12 +852,11 @@ def create_vcs_deployment( VCS reference to create deployment from. Depending on type this can be: branch name, commit hash activate : Optional[bool] Automatically activate the deployment when it is finished building. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -861,33 +867,33 @@ def create_vcs_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if reference is None: raise AppwriteException('Missing required parameter: "reference"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['type'] = self._normalize_value(type) api_params['reference'] = self._normalize_value(reference) if activate is not None: api_params['activate'] = self._normalize_value(activate) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def get_deployment( self, function_id: str, - deployment_id: str + deployment_id: str, ) -> Deployment: """ Get a function deployment by its unique ID. @@ -898,12 +904,11 @@ def get_deployment( Function ID. deployment_id : str Deployment ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -914,26 +919,27 @@ def get_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def delete_deployment( self, function_id: str, - deployment_id: str + deployment_id: str, ) -> Dict[str, Any]: """ Delete a code deployment by its unique ID. @@ -944,12 +950,11 @@ def delete_deployment( Function ID. deployment_id : str Deployment ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -960,28 +965,29 @@ def delete_deployment( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def get_deployment_download( self, function_id: str, deployment_id: str, type: Optional[DeploymentDownloadType] = None, - token: Optional[str] = None + token: Optional[str] = None, ) -> bytes: """ Get a function deployment content by its unique ID. The endpoint response return with a 'Content-Disposition: attachment' header that tells the browser to start downloading the file to user downloads directory. @@ -996,12 +1002,11 @@ def get_deployment_download( Deployment file to download. Can be: "source", "output". token : Optional[str] Presigned source-download token for accessing this deployment without a session (jobs-service). - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -1012,30 +1017,31 @@ def get_deployment_download( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - if type is not None: api_params['type'] = self._normalize_value(type) if token is not None: api_params['token'] = self._normalize_value(token) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': '*/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': '*/*', + }, + api_params, + ) return response - def update_deployment_status( self, function_id: str, - deployment_id: str + deployment_id: str, ) -> Deployment: """ Cancel an ongoing function deployment build. If the build is already in progress, it will be stopped and marked as canceled. If the build hasn't started yet, it will be marked as canceled without executing. You cannot cancel builds that have already completed (status 'ready') or failed. The response includes the final build status and details. @@ -1046,12 +1052,11 @@ def update_deployment_status( Function ID. deployment_id : str Deployment ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1062,28 +1067,29 @@ def update_deployment_status( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def list_executions( self, function_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ExecutionList: """ Get a list of all the current user function execution logs. You can use the query params to filter your results. @@ -1096,12 +1102,11 @@ def list_executions( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: trigger, status, responseStatusCode, duration, requestMethod, requestPath, deploymentId total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ExecutionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1112,22 +1117,24 @@ def list_executions( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ExecutionList) - def create_execution( self, function_id: str, @@ -1136,7 +1143,7 @@ def create_execution( path: Optional[str] = None, method: Optional[ExecutionMethod] = None, headers: Optional[Dict[str, Any]] = None, - scheduled_at: Optional[str] = None + scheduled_at: Optional[str] = None, ) -> Execution: """ Trigger a function execution. The returned object will return you the current execution status. You can ping the `Get Execution` endpoint to get updates on the current execution status. Once this endpoint is called, your function execution process will start asynchronously. @@ -1157,12 +1164,11 @@ def create_execution( HTTP headers of execution. Defaults to empty. scheduled_at : Optional[str] Scheduled execution time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. DateTime value must be in future with precision in minutes. - Returns ------- Execution API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1173,9 +1179,7 @@ def create_execution( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - if body is not None: api_params['body'] = self._normalize_value(body) if xasync is not None: @@ -1189,19 +1193,23 @@ def create_execution( if scheduled_at is not None: api_params['scheduledAt'] = self._normalize_value(scheduled_at) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Execution) - def get_execution( self, function_id: str, - execution_id: str + execution_id: str, ) -> Execution: """ Get a function execution log by its unique ID. @@ -1212,12 +1220,11 @@ def get_execution( Function ID. execution_id : str Execution ID. - Returns ------- Execution API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1228,26 +1235,27 @@ def get_execution( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if execution_id is None: raise AppwriteException('Missing required parameter: "execution_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{executionId}', str(self._normalize_value(execution_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Execution) - def delete_execution( self, function_id: str, - execution_id: str + execution_id: str, ) -> Dict[str, Any]: """ Delete a function execution by its unique ID. @@ -1258,12 +1266,11 @@ def delete_execution( Function ID. execution_id : str Execution ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1274,27 +1281,28 @@ def delete_execution( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if execution_id is None: raise AppwriteException('Missing required parameter: "execution_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{executionId}', str(self._normalize_value(execution_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_variables( self, function_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> VariableList: """ Get a list of all variables of a specific function. @@ -1307,12 +1315,11 @@ def list_variables( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, resourceType, resourceId, secret total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- VariableList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1323,29 +1330,31 @@ def list_variables( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=VariableList) - def create_variable( self, function_id: str, variable_id: str, key: str, value: str, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Create a new function environment variable. These variables can be accessed in the function at runtime as environment variables. @@ -1357,17 +1366,16 @@ def create_variable( variable_id : str Variable ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. key : str - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : str Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only functions can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1378,37 +1386,36 @@ def create_variable( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if value is None: raise AppwriteException('Missing required parameter: "value"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) - api_params['variableId'] = self._normalize_value(variable_id) api_params['key'] = self._normalize_value(key) api_params['value'] = self._normalize_value(value) if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def get_variable( self, function_id: str, - variable_id: str + variable_id: str, ) -> Variable: """ Get a variable by its unique ID. @@ -1419,12 +1426,11 @@ def get_variable( Function unique ID. variable_id : str Variable unique ID. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1435,29 +1441,30 @@ def get_variable( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def update_variable( self, function_id: str, variable_id: str, key: Optional[str] = None, value: Optional[str] = None, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Update variable by its unique ID. @@ -1469,17 +1476,16 @@ def update_variable( variable_id : str Variable unique ID. key : Optional[str] - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : Optional[str] Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only functions can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1490,13 +1496,10 @@ def update_variable( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - if key is not None: api_params['key'] = self._normalize_value(key) if value is not None: @@ -1504,19 +1507,23 @@ def update_variable( if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def delete_variable( self, function_id: str, - variable_id: str + variable_id: str, ) -> Dict[str, Any]: """ Delete a variable by its unique ID. @@ -1527,12 +1534,11 @@ def delete_variable( Function unique ID. variable_id : str Variable unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1543,18 +1549,19 @@ def delete_variable( api_params = {} if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{functionId}', str(self._normalize_value(function_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/graphql.py b/appwrite/services/graphql.py index e0fce562..ed8661b2 100644 --- a/appwrite/services/graphql.py +++ b/appwrite/services/graphql.py @@ -4,6 +4,7 @@ from ..exception import AppwriteException from appwrite.utils.deprecated import deprecated + class Graphql(Service): def __init__(self, client) -> None: @@ -11,7 +12,7 @@ def __init__(self, client) -> None: def query( self, - query: Dict[str, Any] + query: Dict[str, Any], ) -> Dict[str, Any]: """ Execute a GraphQL mutation. @@ -20,12 +21,11 @@ def query( ---------- query : Dict[str, Any] The query or queries to execute. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -36,23 +36,25 @@ def query( api_params = {} if query is None: raise AppwriteException('Missing required parameter: "query"') - - api_params['query'] = self._normalize_value(query) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'x-sdk-graphql': 'true', - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'x-sdk-graphql': 'true', + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def mutation( self, - query: Dict[str, Any] + query: Dict[str, Any], ) -> Dict[str, Any]: """ Execute a GraphQL mutation. @@ -61,12 +63,11 @@ def mutation( ---------- query : Dict[str, Any] The query or queries to execute. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -77,16 +78,18 @@ def mutation( api_params = {} if query is None: raise AppwriteException('Missing required parameter: "query"') - - api_params['query'] = self._normalize_value(query) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'x-sdk-graphql': 'true', - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'x-sdk-graphql': 'true', + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/locale.py b/appwrite/services/locale.py index 678511e5..4a3c96f0 100644 --- a/appwrite/services/locale.py +++ b/appwrite/services/locale.py @@ -11,24 +11,24 @@ from ..models.currency_list import CurrencyList from ..models.language_list import LanguageList + class Locale(Service): def __init__(self, client) -> None: super(Locale, self).__init__(client) def get( - self + self, ) -> LocaleModel: """ Get the current user location based on IP. Returns an object with user country code, country name, continent name, continent code, ip address and suggested currency. You can use the locale header to get the data in a supported language. - - ([IP Geolocation by DB-IP](https://db-ip.com)) + ([IP Geolocation by DB-IP](https://db-ip.com)) Returns ------- LocaleModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -38,25 +38,28 @@ def get( api_path = '/locale' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=LocaleModel) - def list_codes( - self + self, ) -> LocaleCodeList: """ List of all locale codes in [ISO 639-1](https://en.wikipedia.org/wiki/List_of_ISO_639-1_codes). - Returns ------- LocaleCodeList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -66,25 +69,28 @@ def list_codes( api_path = '/locale/codes' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=LocaleCodeList) - def list_continents( - self + self, ) -> ContinentList: """ List of all continents. You can use the locale header to get the data in a supported language. - Returns ------- ContinentList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -94,25 +100,28 @@ def list_continents( api_path = '/locale/continents' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ContinentList) - def list_countries( - self + self, ) -> CountryList: """ List of all countries. You can use the locale header to get the data in a supported language. - Returns ------- CountryList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -122,25 +131,28 @@ def list_countries( api_path = '/locale/countries' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=CountryList) - def list_countries_eu( - self + self, ) -> CountryList: """ List of all countries that are currently members of the EU. You can use the locale header to get the data in a supported language. - Returns ------- CountryList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -150,25 +162,28 @@ def list_countries_eu( api_path = '/locale/countries/eu' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=CountryList) - def list_countries_phones( - self + self, ) -> PhoneList: """ List of all countries phone codes. You can use the locale header to get the data in a supported language. - Returns ------- PhoneList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -178,25 +193,28 @@ def list_countries_phones( api_path = '/locale/countries/phones' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PhoneList) - def list_currencies( - self + self, ) -> CurrencyList: """ List of all currencies, including currency symbol, name, plural, and decimal digits for all major and minor currencies. You can use the locale header to get the data in a supported language. - Returns ------- CurrencyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -206,25 +224,28 @@ def list_currencies( api_path = '/locale/currencies' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=CurrencyList) - def list_languages( - self + self, ) -> LanguageList: """ List of all languages classified by ISO 639-1 including 2-letter code, name in English, and name in the respective language. - Returns ------- LanguageList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -234,10 +255,14 @@ def list_languages( api_path = '/locale/languages' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=LanguageList) - diff --git a/appwrite/services/messaging.py b/appwrite/services/messaging.py index 2ebe2bd6..29a37285 100644 --- a/appwrite/services/messaging.py +++ b/appwrite/services/messaging.py @@ -15,6 +15,7 @@ from ..models.subscriber_list import SubscriberList from ..models.subscriber import Subscriber + class Messaging(Service): def __init__(self, client) -> None: @@ -24,7 +25,7 @@ def list_messages( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> MessageList: """ Get a list of all messages from the current Appwrite project. @@ -37,12 +38,11 @@ def list_messages( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- MessageList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -51,7 +51,6 @@ def list_messages( api_path = '/messaging/messages' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -59,14 +58,18 @@ def list_messages( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MessageList) - def create_email( self, message_id: str, @@ -80,7 +83,7 @@ def create_email( attachments: Optional[List[str]] = None, draft: Optional[bool] = None, html: Optional[bool] = None, - scheduled_at: Optional[str] = None + scheduled_at: Optional[str] = None, ) -> Message: """ Create a new email message. @@ -111,12 +114,11 @@ def create_email( Is content of type HTML scheduled_at : Optional[str] Scheduled delivery time for message in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. DateTime value must be in future. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -127,14 +129,10 @@ def create_email( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - if subject is None: raise AppwriteException('Missing required parameter: "subject"') - if content is None: raise AppwriteException('Missing required parameter: "content"') - - api_params['messageId'] = self._normalize_value(message_id) api_params['subject'] = self._normalize_value(subject) api_params['content'] = self._normalize_value(content) @@ -157,15 +155,19 @@ def create_email( if scheduled_at is not None: api_params['scheduledAt'] = self._normalize_value(scheduled_at) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def update_email( self, message_id: str, @@ -179,11 +181,10 @@ def update_email( cc: Optional[List[str]] = None, bcc: Optional[List[str]] = None, scheduled_at: Optional[str] = None, - attachments: Optional[List[str]] = None + attachments: Optional[List[str]] = None, ) -> Message: """ Update an email message by its unique ID. This endpoint only works on messages that are in draft status. Messages that are already processing, sent, or failed cannot be updated. - Parameters ---------- @@ -211,12 +212,11 @@ def update_email( Scheduled delivery time for message in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. DateTime value must be in future. attachments : Optional[List[str]] Array of compound ID strings of bucket IDs and file IDs to be attached to the email. They should be formatted as :. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -227,9 +227,7 @@ def update_email( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - if topics is not None: api_params['topics'] = self._normalize_value(topics) if users is not None: @@ -253,15 +251,19 @@ def update_email( if attachments is not None: api_params['attachments'] = self._normalize_value(attachments) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def create_push( self, message_id: str, @@ -282,7 +284,7 @@ def create_push( scheduled_at: Optional[str] = None, content_available: Optional[bool] = None, critical: Optional[bool] = None, - priority: Optional[MessagePriority] = None + priority: Optional[MessagePriority] = None, ) -> Message: """ Create a new push notification. @@ -327,12 +329,11 @@ def create_push( If set to true, the notification will be marked as critical. This requires the app to have the critical notification entitlement. Available only for iOS Platform. priority : Optional[MessagePriority] Set the notification priority. "normal" will consider device state and may not deliver notifications immediately. "high" will always attempt to immediately deliver the notification. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -343,8 +344,6 @@ def create_push( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - - api_params['messageId'] = self._normalize_value(message_id) if title is not None: api_params['title'] = self._normalize_value(title) @@ -383,15 +382,19 @@ def create_push( if priority is not None: api_params['priority'] = self._normalize_value(priority) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def update_push( self, message_id: str, @@ -412,11 +415,10 @@ def update_push( scheduled_at: Optional[str] = None, content_available: Optional[bool] = None, critical: Optional[bool] = None, - priority: Optional[MessagePriority] = None + priority: Optional[MessagePriority] = None, ) -> Message: """ Update a push notification by its unique ID. This endpoint only works on messages that are in draft status. Messages that are already processing, sent, or failed cannot be updated. - Parameters ---------- @@ -458,12 +460,11 @@ def update_push( If set to true, the notification will be marked as critical. This requires the app to have the critical notification entitlement. Available only for iOS Platform. priority : Optional[MessagePriority] Set the notification priority. "normal" will consider device battery state and may send notifications later. "high" will always attempt to immediately deliver the notification. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -474,9 +475,7 @@ def update_push( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - if topics is not None: api_params['topics'] = self._normalize_value(topics) if users is not None: @@ -514,15 +513,19 @@ def update_push( if priority is not None: api_params['priority'] = self._normalize_value(priority) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def create_sms( self, message_id: str, @@ -531,7 +534,7 @@ def create_sms( users: Optional[List[str]] = None, targets: Optional[List[str]] = None, draft: Optional[bool] = None, - scheduled_at: Optional[str] = None + scheduled_at: Optional[str] = None, ) -> Message: """ Create a new SMS message. @@ -552,12 +555,11 @@ def create_sms( Is message a draft scheduled_at : Optional[str] Scheduled delivery time for message in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. DateTime value must be in future. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -568,11 +570,8 @@ def create_sms( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - if content is None: raise AppwriteException('Missing required parameter: "content"') - - api_params['messageId'] = self._normalize_value(message_id) api_params['content'] = self._normalize_value(content) if topics is not None: @@ -586,15 +585,19 @@ def create_sms( if scheduled_at is not None: api_params['scheduledAt'] = self._normalize_value(scheduled_at) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def update_sms( self, message_id: str, @@ -603,11 +606,10 @@ def update_sms( targets: Optional[List[str]] = None, content: Optional[str] = None, draft: Optional[bool] = None, - scheduled_at: Optional[str] = None + scheduled_at: Optional[str] = None, ) -> Message: """ Update an SMS message by its unique ID. This endpoint only works on messages that are in draft status. Messages that are already processing, sent, or failed cannot be updated. - Parameters ---------- @@ -625,12 +627,11 @@ def update_sms( Is message a draft scheduled_at : Optional[str] Scheduled delivery time for message in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. DateTime value must be in future. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -641,9 +642,7 @@ def update_sms( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - if topics is not None: api_params['topics'] = self._normalize_value(topics) if users is not None: @@ -657,33 +656,35 @@ def update_sms( if scheduled_at is not None: api_params['scheduledAt'] = self._normalize_value(scheduled_at) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def get_message( self, - message_id: str + message_id: str, ) -> Message: """ Get a message by its unique ID. - Parameters ---------- message_id : str Message ID. - Returns ------- Message API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -694,21 +695,23 @@ def get_message( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Message) - def delete( self, - message_id: str + message_id: str, ) -> Dict[str, Any]: """ Delete a message. If the message is not a draft or scheduled, but has been sent, this will not recall the message. @@ -717,12 +720,11 @@ def delete( ---------- message_id : str Message ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -733,23 +735,25 @@ def delete( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_targets( self, message_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> TargetList: """ Get a list of the targets associated with a message. @@ -762,12 +766,11 @@ def list_targets( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: userId, providerId, identifier, providerType total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- TargetList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -778,27 +781,29 @@ def list_targets( api_params = {} if message_id is None: raise AppwriteException('Missing required parameter: "message_id"') - api_path = api_path.replace('{messageId}', str(self._normalize_value(message_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TargetList) - def list_providers( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ProviderList: """ Get a list of all providers from the current Appwrite project. @@ -811,12 +816,11 @@ def list_providers( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ProviderList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -825,7 +829,6 @@ def list_providers( api_path = '/messaging/providers' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -833,14 +836,18 @@ def list_providers( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProviderList) - def create_apns_provider( self, provider_id: str, @@ -850,7 +857,7 @@ def create_apns_provider( team_id: Optional[str] = None, bundle_id: Optional[str] = None, sandbox: Optional[bool] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Apple Push Notification service provider. @@ -873,12 +880,11 @@ def create_apns_provider( Use APNS sandbox environment. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -889,11 +895,8 @@ def create_apns_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if auth_key is not None: @@ -909,15 +912,19 @@ def create_apns_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_apns_provider( self, provider_id: str, @@ -927,7 +934,7 @@ def update_apns_provider( auth_key_id: Optional[str] = None, team_id: Optional[str] = None, bundle_id: Optional[str] = None, - sandbox: Optional[bool] = None + sandbox: Optional[bool] = None, ) -> Provider: """ Update a Apple Push Notification service provider by its unique ID. @@ -950,12 +957,11 @@ def update_apns_provider( APNS bundle ID. sandbox : Optional[bool] Use APNS sandbox environment. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -966,9 +972,7 @@ def update_apns_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -984,21 +988,25 @@ def update_apns_provider( if sandbox is not None: api_params['sandbox'] = self._normalize_value(sandbox) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_fcm_provider( self, provider_id: str, name: str, service_account_json: Optional[Dict[str, Any]] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Firebase Cloud Messaging provider. @@ -1013,12 +1021,11 @@ def create_fcm_provider( FCM service account JSON. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1029,11 +1036,8 @@ def create_fcm_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if service_account_json is not None: @@ -1041,21 +1045,25 @@ def create_fcm_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_fcm_provider( self, provider_id: str, name: Optional[str] = None, enabled: Optional[bool] = None, - service_account_json: Optional[Dict[str, Any]] = None + service_account_json: Optional[Dict[str, Any]] = None, ) -> Provider: """ Update a Firebase Cloud Messaging provider by its unique ID. @@ -1070,12 +1078,11 @@ def update_fcm_provider( Set as enabled. service_account_json : Optional[Dict[str, Any]] FCM service account JSON. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1086,9 +1093,7 @@ def update_fcm_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -1096,15 +1101,19 @@ def update_fcm_provider( if service_account_json is not None: api_params['serviceAccountJSON'] = self._normalize_value(service_account_json) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_mailgun_provider( self, provider_id: str, @@ -1116,7 +1125,7 @@ def create_mailgun_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Mailgun provider. @@ -1143,12 +1152,11 @@ def create_mailgun_provider( Email set in the reply to field for the mail. Default value is sender email. Reply to email must have reply to name as well. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1159,11 +1167,8 @@ def create_mailgun_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if api_key is not None: @@ -1183,15 +1188,19 @@ def create_mailgun_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_mailgun_provider( self, provider_id: str, @@ -1203,7 +1212,7 @@ def update_mailgun_provider( from_name: Optional[str] = None, from_email: Optional[str] = None, reply_to_name: Optional[str] = None, - reply_to_email: Optional[str] = None + reply_to_email: Optional[str] = None, ) -> Provider: """ Update a Mailgun provider by its unique ID. @@ -1230,12 +1239,11 @@ def update_mailgun_provider( Name set in the reply to field for the mail. Default value is sender name. reply_to_email : Optional[str] Email set in the reply to field for the mail. Default value is sender email. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1246,9 +1254,7 @@ def update_mailgun_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if api_key is not None: @@ -1268,15 +1274,19 @@ def update_mailgun_provider( if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_msg91_provider( self, provider_id: str, @@ -1284,7 +1294,7 @@ def create_msg91_provider( template_id: Optional[str] = None, sender_id: Optional[str] = None, auth_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new MSG91 provider. @@ -1303,12 +1313,11 @@ def create_msg91_provider( Msg91 auth key. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1319,11 +1328,8 @@ def create_msg91_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if template_id is not None: @@ -1335,15 +1341,19 @@ def create_msg91_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_msg91_provider( self, provider_id: str, @@ -1351,7 +1361,7 @@ def update_msg91_provider( enabled: Optional[bool] = None, template_id: Optional[str] = None, sender_id: Optional[str] = None, - auth_key: Optional[str] = None + auth_key: Optional[str] = None, ) -> Provider: """ Update a MSG91 provider by its unique ID. @@ -1370,12 +1380,11 @@ def update_msg91_provider( Msg91 sender ID. auth_key : Optional[str] Msg91 auth key. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1386,9 +1395,7 @@ def update_msg91_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -1400,15 +1407,19 @@ def update_msg91_provider( if auth_key is not None: api_params['authKey'] = self._normalize_value(auth_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_resend_provider( self, provider_id: str, @@ -1418,7 +1429,7 @@ def create_resend_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Resend provider. @@ -1441,12 +1452,11 @@ def create_resend_provider( Email set in the reply to field for the mail. Default value is sender email. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1457,11 +1467,8 @@ def create_resend_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if api_key is not None: @@ -1477,15 +1484,19 @@ def create_resend_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_resend_provider( self, provider_id: str, @@ -1495,7 +1506,7 @@ def update_resend_provider( from_name: Optional[str] = None, from_email: Optional[str] = None, reply_to_name: Optional[str] = None, - reply_to_email: Optional[str] = None + reply_to_email: Optional[str] = None, ) -> Provider: """ Update a Resend provider by its unique ID. @@ -1518,12 +1529,11 @@ def update_resend_provider( Name set in the Reply To field for the mail. Default value is Sender Name. reply_to_email : Optional[str] Email set in the Reply To field for the mail. Default value is Sender Email. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1534,9 +1544,7 @@ def update_resend_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -1552,15 +1560,19 @@ def update_resend_provider( if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_sendgrid_provider( self, provider_id: str, @@ -1570,7 +1582,7 @@ def create_sendgrid_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Sendgrid provider. @@ -1593,12 +1605,11 @@ def create_sendgrid_provider( Email set in the reply to field for the mail. Default value is sender email. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1609,11 +1620,8 @@ def create_sendgrid_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if api_key is not None: @@ -1629,15 +1637,19 @@ def create_sendgrid_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_sendgrid_provider( self, provider_id: str, @@ -1647,7 +1659,7 @@ def update_sendgrid_provider( from_name: Optional[str] = None, from_email: Optional[str] = None, reply_to_name: Optional[str] = None, - reply_to_email: Optional[str] = None + reply_to_email: Optional[str] = None, ) -> Provider: """ Update a Sendgrid provider by its unique ID. @@ -1670,12 +1682,11 @@ def update_sendgrid_provider( Name set in the Reply To field for the mail. Default value is Sender Name. reply_to_email : Optional[str] Email set in the Reply To field for the mail. Default value is Sender Email. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1686,9 +1697,7 @@ def update_sendgrid_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -1704,15 +1713,19 @@ def update_sendgrid_provider( if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_ses_provider( self, provider_id: str, @@ -1724,7 +1737,7 @@ def create_ses_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Amazon SES provider. @@ -1751,12 +1764,11 @@ def create_ses_provider( Email set in the reply to field for the mail. Default value is sender email. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1767,11 +1779,8 @@ def create_ses_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if access_key is not None: @@ -1791,15 +1800,19 @@ def create_ses_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_ses_provider( self, provider_id: str, @@ -1811,7 +1824,7 @@ def update_ses_provider( from_name: Optional[str] = None, from_email: Optional[str] = None, reply_to_name: Optional[str] = None, - reply_to_email: Optional[str] = None + reply_to_email: Optional[str] = None, ) -> Provider: """ Update an Amazon SES provider by its unique ID. @@ -1838,12 +1851,11 @@ def update_ses_provider( Name set in the Reply To field for the mail. Default value is Sender Name. reply_to_email : Optional[str] Email set in the Reply To field for the mail. Default value is Sender Email. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1854,9 +1866,7 @@ def update_ses_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -1876,15 +1886,19 @@ def update_ses_provider( if reply_to_email is not None: api_params['replyToEmail'] = self._normalize_value(reply_to_email) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_smtp_provider( self, provider_id: str, @@ -1900,7 +1914,7 @@ def create_smtp_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new SMTP provider. @@ -1935,12 +1949,11 @@ def create_smtp_provider( Email set in the reply to field for the mail. Default value is sender email. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1951,14 +1964,10 @@ def create_smtp_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if host is None: raise AppwriteException('Missing required parameter: "host"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) api_params['host'] = self._normalize_value(host) @@ -1985,15 +1994,19 @@ def create_smtp_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_smtp_provider( self, provider_id: str, @@ -2009,7 +2022,7 @@ def update_smtp_provider( from_email: Optional[str] = None, reply_to_name: Optional[str] = None, reply_to_email: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Update a SMTP provider by its unique ID. @@ -2044,12 +2057,11 @@ def update_smtp_provider( Email set in the Reply To field for the mail. Default value is Sender Email. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2060,9 +2072,7 @@ def update_smtp_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if host is not None: @@ -2090,15 +2100,19 @@ def update_smtp_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_telesign_provider( self, provider_id: str, @@ -2106,7 +2120,7 @@ def create_telesign_provider( xfrom: Optional[str] = None, customer_id: Optional[str] = None, api_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Telesign provider. @@ -2125,12 +2139,11 @@ def create_telesign_provider( Telesign API key. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2141,11 +2154,8 @@ def create_telesign_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if xfrom is not None: @@ -2157,15 +2167,19 @@ def create_telesign_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_telesign_provider( self, provider_id: str, @@ -2173,7 +2187,7 @@ def update_telesign_provider( enabled: Optional[bool] = None, customer_id: Optional[str] = None, api_key: Optional[str] = None, - xfrom: Optional[str] = None + xfrom: Optional[str] = None, ) -> Provider: """ Update a Telesign provider by its unique ID. @@ -2192,12 +2206,11 @@ def update_telesign_provider( Telesign API key. xfrom : Optional[str] Sender number. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2208,9 +2221,7 @@ def update_telesign_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -2222,15 +2233,19 @@ def update_telesign_provider( if xfrom is not None: api_params['from'] = self._normalize_value(xfrom) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_textmagic_provider( self, provider_id: str, @@ -2238,7 +2253,7 @@ def create_textmagic_provider( xfrom: Optional[str] = None, username: Optional[str] = None, api_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Textmagic provider. @@ -2257,12 +2272,11 @@ def create_textmagic_provider( Textmagic apiKey. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2273,11 +2287,8 @@ def create_textmagic_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if xfrom is not None: @@ -2289,15 +2300,19 @@ def create_textmagic_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_textmagic_provider( self, provider_id: str, @@ -2305,7 +2320,7 @@ def update_textmagic_provider( enabled: Optional[bool] = None, username: Optional[str] = None, api_key: Optional[str] = None, - xfrom: Optional[str] = None + xfrom: Optional[str] = None, ) -> Provider: """ Update a Textmagic provider by its unique ID. @@ -2324,12 +2339,11 @@ def update_textmagic_provider( Textmagic apiKey. xfrom : Optional[str] Sender number. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2340,9 +2354,7 @@ def update_textmagic_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -2354,15 +2366,19 @@ def update_textmagic_provider( if xfrom is not None: api_params['from'] = self._normalize_value(xfrom) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_twilio_provider( self, provider_id: str, @@ -2370,7 +2386,7 @@ def create_twilio_provider( xfrom: Optional[str] = None, account_sid: Optional[str] = None, auth_token: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Twilio provider. @@ -2389,12 +2405,11 @@ def create_twilio_provider( Twilio authentication token. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2405,11 +2420,8 @@ def create_twilio_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if xfrom is not None: @@ -2421,15 +2433,19 @@ def create_twilio_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_twilio_provider( self, provider_id: str, @@ -2437,7 +2453,7 @@ def update_twilio_provider( enabled: Optional[bool] = None, account_sid: Optional[str] = None, auth_token: Optional[str] = None, - xfrom: Optional[str] = None + xfrom: Optional[str] = None, ) -> Provider: """ Update a Twilio provider by its unique ID. @@ -2456,12 +2472,11 @@ def update_twilio_provider( Twilio authentication token. xfrom : Optional[str] Sender number. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2472,9 +2487,7 @@ def update_twilio_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -2486,15 +2499,19 @@ def update_twilio_provider( if xfrom is not None: api_params['from'] = self._normalize_value(xfrom) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def create_vonage_provider( self, provider_id: str, @@ -2502,7 +2519,7 @@ def create_vonage_provider( xfrom: Optional[str] = None, api_key: Optional[str] = None, api_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> Provider: """ Create a new Vonage provider. @@ -2521,12 +2538,11 @@ def create_vonage_provider( Vonage API secret. enabled : Optional[bool] Set as enabled. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2537,11 +2553,8 @@ def create_vonage_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['providerId'] = self._normalize_value(provider_id) api_params['name'] = self._normalize_value(name) if xfrom is not None: @@ -2553,15 +2566,19 @@ def create_vonage_provider( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def update_vonage_provider( self, provider_id: str, @@ -2569,7 +2586,7 @@ def update_vonage_provider( enabled: Optional[bool] = None, api_key: Optional[str] = None, api_secret: Optional[str] = None, - xfrom: Optional[str] = None + xfrom: Optional[str] = None, ) -> Provider: """ Update a Vonage provider by its unique ID. @@ -2588,12 +2605,11 @@ def update_vonage_provider( Vonage API secret. xfrom : Optional[str] Sender number. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2604,9 +2620,7 @@ def update_vonage_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -2618,33 +2632,35 @@ def update_vonage_provider( if xfrom is not None: api_params['from'] = self._normalize_value(xfrom) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def get_provider( self, - provider_id: str + provider_id: str, ) -> Provider: """ Get a provider by its unique ID. - Parameters ---------- provider_id : str Provider ID. - Returns ------- Provider API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2655,21 +2671,23 @@ def get_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Provider) - def delete_provider( self, - provider_id: str + provider_id: str, ) -> Dict[str, Any]: """ Delete a provider by its unique ID. @@ -2678,12 +2696,11 @@ def delete_provider( ---------- provider_id : str Provider ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -2694,23 +2711,25 @@ def delete_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_topics( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> TopicList: """ Get a list of all topics from the current Appwrite project. @@ -2723,12 +2742,11 @@ def list_topics( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- TopicList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2737,7 +2755,6 @@ def list_topics( api_path = '/messaging/topics' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -2745,19 +2762,23 @@ def list_topics( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TopicList) - def create_topic( self, topic_id: str, name: str, - subscribe: Optional[List[str]] = None + subscribe: Optional[List[str]] = None, ) -> Topic: """ Create a new topic. @@ -2770,12 +2791,11 @@ def create_topic( Topic Name. subscribe : Optional[List[str]] An array of role strings with subscribe permission. By default all users are granted with any subscribe permission. [learn more about roles](https://appwrite.io/docs/permissions#permission-roles). Maximum of 100 roles are allowed, each 64 characters long. - Returns ------- Topic API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2786,43 +2806,42 @@ def create_topic( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['topicId'] = self._normalize_value(topic_id) api_params['name'] = self._normalize_value(name) if subscribe is not None: api_params['subscribe'] = self._normalize_value(subscribe) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Topic) - def get_topic( self, - topic_id: str + topic_id: str, ) -> Topic: """ Get a topic by its unique ID. - Parameters ---------- topic_id : str Topic ID. - Returns ------- Topic API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2833,27 +2852,28 @@ def get_topic( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Topic) - def update_topic( self, topic_id: str, name: Optional[str] = None, - subscribe: Optional[List[str]] = None + subscribe: Optional[List[str]] = None, ) -> Topic: """ Update a topic by its unique ID. - Parameters ---------- @@ -2863,12 +2883,11 @@ def update_topic( Topic Name. subscribe : Optional[List[str]] An array of role strings with subscribe permission. By default all users are granted with any subscribe permission. [learn more about roles](https://appwrite.io/docs/permissions#permission-roles). Maximum of 100 roles are allowed, each 64 characters long. - Returns ------- Topic API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2879,26 +2898,28 @@ def update_topic( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if subscribe is not None: api_params['subscribe'] = self._normalize_value(subscribe) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Topic) - def delete_topic( self, - topic_id: str + topic_id: str, ) -> Dict[str, Any]: """ Delete a topic by its unique ID. @@ -2907,12 +2928,11 @@ def delete_topic( ---------- topic_id : str Topic ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -2923,24 +2943,26 @@ def delete_topic( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_subscribers( self, topic_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> SubscriberList: """ Get a list of all subscribers from the current Appwrite project. @@ -2955,12 +2977,11 @@ def list_subscribers( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- SubscriberList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2971,9 +2992,7 @@ def list_subscribers( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -2981,19 +3000,23 @@ def list_subscribers( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SubscriberList) - def create_subscriber( self, topic_id: str, subscriber_id: str, - target_id: str + target_id: str, ) -> Subscriber: """ Create a new subscriber. @@ -3006,12 +3029,11 @@ def create_subscriber( Subscriber ID. Choose a custom Subscriber ID or a new Subscriber ID. target_id : str Target ID. The target ID to link to the specified Topic ID. - Returns ------- Subscriber API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3022,35 +3044,34 @@ def create_subscriber( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - if subscriber_id is None: raise AppwriteException('Missing required parameter: "subscriber_id"') - if target_id is None: raise AppwriteException('Missing required parameter: "target_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) - api_params['subscriberId'] = self._normalize_value(subscriber_id) api_params['targetId'] = self._normalize_value(target_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Subscriber) - def get_subscriber( self, topic_id: str, - subscriber_id: str + subscriber_id: str, ) -> Subscriber: """ Get a subscriber by its unique ID. - Parameters ---------- @@ -3058,12 +3079,11 @@ def get_subscriber( Topic ID. The topic ID subscribed to. subscriber_id : str Subscriber ID. - Returns ------- Subscriber API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3074,26 +3094,27 @@ def get_subscriber( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - if subscriber_id is None: raise AppwriteException('Missing required parameter: "subscriber_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) api_path = api_path.replace('{subscriberId}', str(self._normalize_value(subscriber_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Subscriber) - def delete_subscriber( self, topic_id: str, - subscriber_id: str + subscriber_id: str, ) -> Dict[str, Any]: """ Delete a subscriber by its unique ID. @@ -3104,12 +3125,11 @@ def delete_subscriber( Topic ID. The topic ID subscribed to. subscriber_id : str Subscriber ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -3120,18 +3140,19 @@ def delete_subscriber( api_params = {} if topic_id is None: raise AppwriteException('Missing required parameter: "topic_id"') - if subscriber_id is None: raise AppwriteException('Missing required parameter: "subscriber_id"') - api_path = api_path.replace('{topicId}', str(self._normalize_value(topic_id))) api_path = api_path.replace('{subscriberId}', str(self._normalize_value(subscriber_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/mongo.py b/appwrite/services/mongo.py new file mode 100644 index 00000000..7d0e2722 --- /dev/null +++ b/appwrite/services/mongo.py @@ -0,0 +1,1692 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..models.dedicated_database_list import DedicatedDatabaseList +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from ..models.dedicated_database_backup_list import DedicatedDatabaseBackupList +from ..models.dedicated_database_backup import DedicatedDatabaseBackup +from ..models.backup_policy_list import BackupPolicyList +from ..models.backup_policy import BackupPolicy +from ..models.dedicated_database_backup_storage import DedicatedDatabaseBackupStorage +from ..models.dedicated_database_branch_list import DedicatedDatabaseBranchList +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList +from ..models.dedicated_database_pitr_windows import DedicatedDatabasePITRWindows +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.dedicated_database_restoration_list import DedicatedDatabaseRestorationList +from ..models.dedicated_database_restoration import DedicatedDatabaseRestoration +from ..models.database_status import DatabaseStatus + + +class Mongo(Service): + + def __init__(self, client) -> None: + super(Mongo, self).__init__(client) + + def list( + self, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseList: + """ + List all dedicated databases. Results support pagination. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings. + Returns + ------- + DedicatedDatabaseList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseList) + + def create( + self, + database_id: str, + name: str, + version: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create a new dedicated database with the chosen engine and configuration. Status will be 'provisioning' until the database is ready. + + Parameters + ---------- + database_id : str + Database ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Database display name. Max length: 128 chars. + version : Optional[str] + Database engine version. Defaults to latest for selected engine. + specification : Optional[str] + Specification identifier. Drives the allocated CPU, memory, storage, storage class, and connection ceiling. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds. + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes of inactivity before container scales to zero. + pitr : Optional[bool] + Enable point-in-time recovery (PITR). Continuously archives changes so the database can be restored to any moment within the retention window. + pitr_retention_days : Optional[float] + Number of days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_params['databaseId'] = self._normalize_value(database_id) + api_params['name'] = self._normalize_value(name) + if version is not None: + api_params['version'] = self._normalize_value(version) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_specifications( + self, + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/specifications' + api_params = {} + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def get( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Get a dedicated database by its unique ID. Returns the database configuration and current status. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update( + self, + database_id: str, + name: Optional[str] = None, + status: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + metrics_trace_sample_rate: Optional[float] = None, + metrics_slow_query_log_threshold_ms: Optional[float] = None, + sql_api_enabled: Optional[bool] = None, + sql_api_allowed_statements: Optional[List[str]] = None, + sql_api_max_rows: Optional[float] = None, + sql_api_max_bytes: Optional[float] = None, + sql_api_timeout_seconds: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Update a dedicated database configuration. All changes are applied with zero downtime. Specification changes (cpu, memory, storage) are handled via rolling cutover. Storage expansion is done online. All other settings are applied in-place. + + Parameters + ---------- + database_id : str + Database ID. + name : Optional[str] + Database display name. + status : Optional[str] + Database status. Allowed values: ready, paused, inactive. Set to "paused" to pause, "ready" to resume (also recovers a failed database whose infrastructure is healthy), or "inactive" to spin down a shared-pool database. + specification : Optional[str] + Specification. Changes cpu, memory, storage, connection ceiling, and node pool based on specification config. Resource changes are applied via rolling cutover with zero downtime. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds (60-86400). + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes before container scales to zero. + pitr : Optional[bool] + Enable or disable point-in-time recovery (PITR). + pitr_retention_days : Optional[float] + Days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + metrics_trace_sample_rate : Optional[float] + Fraction of queries to trace (0.0–1.0). Forwarded to the sidecar. + metrics_slow_query_log_threshold_ms : Optional[float] + Threshold in ms above which queries are logged as slow. Forwarded to the sidecar. + sql_api_enabled : Optional[bool] + Enable the SQL API sidecar for this database. + sql_api_allowed_statements : Optional[List[str]] + Statement types the SQL API accepts. Allowed values: SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, DROP, TRUNCATE, GRANT, REVOKE. + sql_api_max_rows : Optional[float] + Maximum rows returned per SQL API execution (1-1000000). + sql_api_max_bytes : Optional[float] + Maximum serialised SQL API result payload in bytes (1024-104857600). + sql_api_timeout_seconds : Optional[float] + Per-call SQL API execution timeout in seconds (1-300). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if status is not None: + api_params['status'] = self._normalize_value(status) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + if metrics_trace_sample_rate is not None: + api_params['metricsTraceSampleRate'] = self._normalize_value(metrics_trace_sample_rate) + if metrics_slow_query_log_threshold_ms is not None: + api_params['metricsSlowQueryLogThresholdMs'] = self._normalize_value(metrics_slow_query_log_threshold_ms) + if sql_api_enabled is not None: + api_params['sqlApiEnabled'] = self._normalize_value(sql_api_enabled) + if sql_api_allowed_statements is not None: + api_params['sqlApiAllowedStatements'] = self._normalize_value(sql_api_allowed_statements) + if sql_api_max_rows is not None: + api_params['sqlApiMaxRows'] = self._normalize_value(sql_api_max_rows) + if sql_api_max_bytes is not None: + api_params['sqlApiMaxBytes'] = self._normalize_value(sql_api_max_bytes) + if sql_api_timeout_seconds is not None: + api_params['sqlApiTimeoutSeconds'] = self._normalize_value(sql_api_timeout_seconds) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete( + self, + database_id: str, + ) -> Dict[str, Any]: + """ + Delete a dedicated database. This action is irreversible. The database status will be set to 'deleting' and all resources will be cleaned up. Deletion is allowed from any state, and repeating the call re-dispatches the cleanup. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_backups( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseBackupList: + """ + List all backups for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: status, type, databaseId + Returns + ------- + DedicatedDatabaseBackupList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupList) + + def create_backup( + self, + database_id: str, + type: Optional[str] = None, + ) -> DedicatedDatabaseBackup: + """ + Create a manual backup of a dedicated database. The backup will be created asynchronously and its status can be checked via the get backup endpoint. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Backup type: full or incremental. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def list_backup_policies( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> BackupPolicyList: + """ + List scheduled backup policies for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. + Returns + ------- + BackupPolicyList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicyList) + + def create_backup_policy( + self, + database_id: str, + policy_id: str, + name: str, + schedule: str, + retention: float, + type: Optional[str] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Create a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Policy name. Max length: 128 chars. + schedule : str + Schedule CRON syntax. + retention : float + Days to keep backups before deletion. + type : Optional[str] + Backup type: full or incremental. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + if schedule is None: + raise AppwriteException('Missing required parameter: "schedule"') + if retention is None: + raise AppwriteException('Missing required parameter: "retention"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['policyId'] = self._normalize_value(policy_id) + api_params['name'] = self._normalize_value(name) + api_params['schedule'] = self._normalize_value(schedule) + api_params['retention'] = self._normalize_value(retention) + if type is not None: + api_params['type'] = self._normalize_value(type) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def get_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> BackupPolicy: + """ + Get a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def update_backup_policy( + self, + database_id: str, + policy_id: str, + name: Optional[str] = None, + schedule: Optional[str] = None, + retention: Optional[float] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Update a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + name : Optional[str] + Policy name. Max length: 128 chars. + schedule : Optional[str] + Schedule CRON syntax. + retention : Optional[float] + Days to keep backups before deletion. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if schedule is not None: + api_params['schedule'] = self._normalize_value(schedule) + if retention is not None: + api_params['retention'] = self._normalize_value(retention) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def delete_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> Dict[str, Any]: + """ + Delete a scheduled backup policy for a dedicated database. Backups already taken by the policy are kept until their retention expires. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def update_backup_storage( + self, + database_id: str, + provider: str, + bucket: str, + access_key: str, + secret_key: str, + region: Optional[str] = None, + prefix: Optional[str] = None, + endpoint: Optional[str] = None, + ) -> DedicatedDatabaseBackupStorage: + """ + Configure off-cluster backup storage for a dedicated database. Supports S3, GCS, and Azure Blob Storage destinations. Backups will be stored to the configured destination in addition to on-cluster storage. + + Parameters + ---------- + database_id : str + Database ID. + provider : str + Storage provider for off-cluster backups. Allowed values: s3 (Amazon S3 or S3-compatible), gcs (Google Cloud Storage), azure (Azure Blob Storage). + bucket : str + Storage bucket or container name. + access_key : str + Access key or client ID for authentication. + secret_key : str + Secret key or service account JSON for authentication. + region : Optional[str] + Storage region. + prefix : Optional[str] + Object key prefix for backups. + endpoint : Optional[str] + Custom endpoint for S3-compatible storage (e.g. MinIO). + Returns + ------- + DedicatedDatabaseBackupStorage + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/storage' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if provider is None: + raise AppwriteException('Missing required parameter: "provider"') + if bucket is None: + raise AppwriteException('Missing required parameter: "bucket"') + if access_key is None: + raise AppwriteException('Missing required parameter: "access_key"') + if secret_key is None: + raise AppwriteException('Missing required parameter: "secret_key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['provider'] = self._normalize_value(provider) + api_params['bucket'] = self._normalize_value(bucket) + if region is not None: + api_params['region'] = self._normalize_value(region) + if prefix is not None: + api_params['prefix'] = self._normalize_value(prefix) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + api_params['accessKey'] = self._normalize_value(access_key) + api_params['secretKey'] = self._normalize_value(secret_key) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupStorage) + + def get_backup( + self, + database_id: str, + backup_id: str, + ) -> DedicatedDatabaseBackup: + """ + Get details of a specific database backup including its status, size, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def delete_backup( + self, + database_id: str, + backup_id: str, + ) -> Dict[str, Any]: + """ + Delete a database backup. This will permanently remove the backup from storage and cannot be undone. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_branches( + self, + database_id: str, + ) -> DedicatedDatabaseBranchList: + """ + List all ephemeral branches for a dedicated database. Returns branch metadata including ID, name, namespace, and expiration time. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseBranchList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBranchList) + + def create_branch( + self, + database_id: str, + branch_id: Optional[str] = None, + ttl: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create an ephemeral database branch from the primary via PVC snapshot. The branch is a full copy of the database at the current point in time, useful for testing schema migrations or running experiments without affecting production data. Branches expire after the configured TTL (default 24 hours). The branch is created asynchronously. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : Optional[str] + Branch ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + ttl : Optional[float] + Time-to-live in seconds before the branch expires. Min 300 (5 min), max 604800 (7 days). Default: 86400 (24h). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if branch_id is not None: + api_params['branchId'] = self._normalize_value(branch_id) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete_branch( + self, + database_id: str, + branch_id: str, + ) -> DedicatedDatabase: + """ + Delete an ephemeral database branch. This removes the branch namespace, its PVC, and the associated VolumeSnapshot. The deletion runs asynchronously and is irreversible. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : str + Branch ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/branches/{branchId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if branch_id is None: + raise AppwriteException('Missing required parameter: "branch_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{branchId}', str(self._normalize_value(branch_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_credentials( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Rotate the primary connection credentials for a dedicated database. Generates a new password and updates the database atomically. Previous credentials stop working immediately. Returns the database with a refreshed connection string carrying the new password. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/credentials' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_maintenance( + self, + database_id: str, + day: str, + hour_utc: float, + ) -> DedicatedDatabase: + """ + Update the maintenance window for a dedicated database. Maintenance operations like minor version upgrades will be performed during this window. + + Parameters + ---------- + database_id : str + Database ID. + day : str + Day of the week for the maintenance window. Allowed values: sun, mon, tue, wed, thu, fri, sat. + hour_utc : float + Hour in UTC (0-23) for maintenance window start. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/maintenance' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if day is None: + raise AppwriteException('Missing required parameter: "day"') + if hour_utc is None: + raise AppwriteException('Missing required parameter: "hour_utc"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['day'] = self._normalize_value(day) + api_params['hourUtc'] = self._normalize_value(hour_utc) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_migration( + self, + database_id: str, + target_type: str, + specification: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Migrate a database between shared and dedicated types. Shared to dedicated provisions an always-on dedicated instance; dedicated to shared converts to a serverless instance that scales to zero when idle. Data is copied to the target with a brief read-only window during cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_type : str + Target database type to migrate to. Allowed values: shared (serverless, scales to zero when idle), dedicated (always-on with persistent resources). + specification : Optional[str] + Target specification to provision when migrating to dedicated. Ignored for shared. Defaults to the database's current specification. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/migrations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_type is None: + raise AppwriteException('Missing required parameter: "target_type"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetType'] = self._normalize_value(target_type) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_pitr( + self, + database_id: str, + ) -> DedicatedDatabasePITRWindows: + """ + Get available point-in-time recovery windows for a dedicated database. Returns the earliest and latest recovery points. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabasePITRWindows + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/pitr' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePITRWindows) + + def get_replicas( + self, + database_id: str, + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + def list_restorations( + self, + database_id: str, + status: Optional[str] = None, + type: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseRestorationList: + """ + List all restorations for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by restoration status. + type : Optional[str] + Filter by restoration type. + limit : Optional[float] + Maximum number of restorations to return. + offset : Optional[float] + Number of restorations to skip. + Returns + ------- + DedicatedDatabaseRestorationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if type is not None: + api_params['type'] = self._normalize_value(type) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestorationList) + + def create_restoration( + self, + database_id: str, + type: Optional[str] = None, + backup_id: Optional[str] = None, + target_database_id: Optional[str] = None, + target_time: Optional[str] = None, + ) -> DedicatedDatabaseRestoration: + """ + Restore a database from a backup or to a specific point in time (PITR). For backup restoration, provide a backupId. For PITR, provide a targetTime as an ISO 8601 datetime. PITR requires the database to have PITR enabled and is only available for enterprise databases. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Restoration type. Allowed values: backup, pitr. Use "backup" to restore from a specific backup, or "pitr" for point-in-time recovery. + backup_id : Optional[str] + Backup ID to restore from (required for backup type). + target_database_id : Optional[str] + Existing database ID to restore into. The target must be distinct, ready, and use the same engine and version. + target_time : Optional[str] + Target time for PITR (required for pitr type) as an [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) datetime. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + if backup_id is not None: + api_params['backupId'] = self._normalize_value(backup_id) + if target_database_id is not None: + api_params['targetDatabaseId'] = self._normalize_value(target_database_id) + if target_time is not None: + api_params['targetTime'] = self._normalize_value(target_time) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_restoration( + self, + database_id: str, + restoration_id: str, + ) -> DedicatedDatabaseRestoration: + """ + Get details of a specific database restoration including its status, type, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + restoration_id : str + Restoration ID. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/restorations/{restorationId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if restoration_id is None: + raise AppwriteException('Missing required parameter: "restoration_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{restorationId}', str(self._normalize_value(restoration_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_status( + self, + database_id: str, + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseStatus) + + def create_upgrade( + self, + database_id: str, + target_version: str, + ) -> DedicatedDatabase: + """ + Upgrade a dedicated database to a new engine version. Uses blue-green deployment for zero-downtime cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_version : str + Target engine version to upgrade to. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mongo/{databaseId}/upgrades' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_version is None: + raise AppwriteException('Missing required parameter: "target_version"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetVersion'] = self._normalize_value(target_version) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) diff --git a/appwrite/services/mysql.py b/appwrite/services/mysql.py new file mode 100644 index 00000000..aa567815 --- /dev/null +++ b/appwrite/services/mysql.py @@ -0,0 +1,1872 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..models.dedicated_database_list import DedicatedDatabaseList +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from ..models.dedicated_database_backup_list import DedicatedDatabaseBackupList +from ..models.dedicated_database_backup import DedicatedDatabaseBackup +from ..models.backup_policy_list import BackupPolicyList +from ..models.backup_policy import BackupPolicy +from ..models.dedicated_database_backup_storage import DedicatedDatabaseBackupStorage +from ..models.dedicated_database_branch_list import DedicatedDatabaseBranchList +from ..models.dedicated_database_execution import DedicatedDatabaseExecution +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList +from ..models.dedicated_database_pitr_windows import DedicatedDatabasePITRWindows +from ..models.dedicated_database_pooler import DedicatedDatabasePooler +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.dedicated_database_restoration_list import DedicatedDatabaseRestorationList +from ..models.dedicated_database_restoration import DedicatedDatabaseRestoration +from ..models.database_status import DatabaseStatus + + +class Mysql(Service): + + def __init__(self, client) -> None: + super(Mysql, self).__init__(client) + + def list( + self, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseList: + """ + List all dedicated databases. Results support pagination. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings. + Returns + ------- + DedicatedDatabaseList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseList) + + def create( + self, + database_id: str, + name: str, + version: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create a new dedicated database with the chosen engine and configuration. Status will be 'provisioning' until the database is ready. + + Parameters + ---------- + database_id : str + Database ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Database display name. Max length: 128 chars. + version : Optional[str] + Database engine version. Defaults to latest for selected engine. + specification : Optional[str] + Specification identifier. Drives the allocated CPU, memory, storage, storage class, and connection ceiling. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds. + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes of inactivity before container scales to zero. + pitr : Optional[bool] + Enable point-in-time recovery (PITR). Continuously archives changes so the database can be restored to any moment within the retention window. + pitr_retention_days : Optional[float] + Number of days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_params['databaseId'] = self._normalize_value(database_id) + api_params['name'] = self._normalize_value(name) + if version is not None: + api_params['version'] = self._normalize_value(version) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_specifications( + self, + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/specifications' + api_params = {} + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def get( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Get a dedicated database by its unique ID. Returns the database configuration and current status. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update( + self, + database_id: str, + name: Optional[str] = None, + status: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + metrics_trace_sample_rate: Optional[float] = None, + metrics_slow_query_log_threshold_ms: Optional[float] = None, + sql_api_enabled: Optional[bool] = None, + sql_api_allowed_statements: Optional[List[str]] = None, + sql_api_max_rows: Optional[float] = None, + sql_api_max_bytes: Optional[float] = None, + sql_api_timeout_seconds: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Update a dedicated database configuration. All changes are applied with zero downtime. Specification changes (cpu, memory, storage) are handled via rolling cutover. Storage expansion is done online. All other settings are applied in-place. + + Parameters + ---------- + database_id : str + Database ID. + name : Optional[str] + Database display name. + status : Optional[str] + Database status. Allowed values: ready, paused, inactive. Set to "paused" to pause, "ready" to resume (also recovers a failed database whose infrastructure is healthy), or "inactive" to spin down a shared-pool database. + specification : Optional[str] + Specification. Changes cpu, memory, storage, connection ceiling, and node pool based on specification config. Resource changes are applied via rolling cutover with zero downtime. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds (60-86400). + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes before container scales to zero. + pitr : Optional[bool] + Enable or disable point-in-time recovery (PITR). + pitr_retention_days : Optional[float] + Days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + metrics_trace_sample_rate : Optional[float] + Fraction of queries to trace (0.0–1.0). Forwarded to the sidecar. + metrics_slow_query_log_threshold_ms : Optional[float] + Threshold in ms above which queries are logged as slow. Forwarded to the sidecar. + sql_api_enabled : Optional[bool] + Enable the SQL API sidecar for this database. + sql_api_allowed_statements : Optional[List[str]] + Statement types the SQL API accepts. Allowed values: SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, DROP, TRUNCATE, GRANT, REVOKE. + sql_api_max_rows : Optional[float] + Maximum rows returned per SQL API execution (1-1000000). + sql_api_max_bytes : Optional[float] + Maximum serialised SQL API result payload in bytes (1024-104857600). + sql_api_timeout_seconds : Optional[float] + Per-call SQL API execution timeout in seconds (1-300). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if status is not None: + api_params['status'] = self._normalize_value(status) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + if metrics_trace_sample_rate is not None: + api_params['metricsTraceSampleRate'] = self._normalize_value(metrics_trace_sample_rate) + if metrics_slow_query_log_threshold_ms is not None: + api_params['metricsSlowQueryLogThresholdMs'] = self._normalize_value(metrics_slow_query_log_threshold_ms) + if sql_api_enabled is not None: + api_params['sqlApiEnabled'] = self._normalize_value(sql_api_enabled) + if sql_api_allowed_statements is not None: + api_params['sqlApiAllowedStatements'] = self._normalize_value(sql_api_allowed_statements) + if sql_api_max_rows is not None: + api_params['sqlApiMaxRows'] = self._normalize_value(sql_api_max_rows) + if sql_api_max_bytes is not None: + api_params['sqlApiMaxBytes'] = self._normalize_value(sql_api_max_bytes) + if sql_api_timeout_seconds is not None: + api_params['sqlApiTimeoutSeconds'] = self._normalize_value(sql_api_timeout_seconds) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete( + self, + database_id: str, + ) -> Dict[str, Any]: + """ + Delete a dedicated database. This action is irreversible. The database status will be set to 'deleting' and all resources will be cleaned up. Deletion is allowed from any state, and repeating the call re-dispatches the cleanup. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_backups( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseBackupList: + """ + List all backups for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: status, type, databaseId + Returns + ------- + DedicatedDatabaseBackupList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupList) + + def create_backup( + self, + database_id: str, + type: Optional[str] = None, + ) -> DedicatedDatabaseBackup: + """ + Create a manual backup of a dedicated database. The backup will be created asynchronously and its status can be checked via the get backup endpoint. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Backup type: full or incremental. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def list_backup_policies( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> BackupPolicyList: + """ + List scheduled backup policies for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. + Returns + ------- + BackupPolicyList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicyList) + + def create_backup_policy( + self, + database_id: str, + policy_id: str, + name: str, + schedule: str, + retention: float, + type: Optional[str] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Create a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Policy name. Max length: 128 chars. + schedule : str + Schedule CRON syntax. + retention : float + Days to keep backups before deletion. + type : Optional[str] + Backup type: full or incremental. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + if schedule is None: + raise AppwriteException('Missing required parameter: "schedule"') + if retention is None: + raise AppwriteException('Missing required parameter: "retention"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['policyId'] = self._normalize_value(policy_id) + api_params['name'] = self._normalize_value(name) + api_params['schedule'] = self._normalize_value(schedule) + api_params['retention'] = self._normalize_value(retention) + if type is not None: + api_params['type'] = self._normalize_value(type) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def get_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> BackupPolicy: + """ + Get a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def update_backup_policy( + self, + database_id: str, + policy_id: str, + name: Optional[str] = None, + schedule: Optional[str] = None, + retention: Optional[float] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Update a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + name : Optional[str] + Policy name. Max length: 128 chars. + schedule : Optional[str] + Schedule CRON syntax. + retention : Optional[float] + Days to keep backups before deletion. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if schedule is not None: + api_params['schedule'] = self._normalize_value(schedule) + if retention is not None: + api_params['retention'] = self._normalize_value(retention) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def delete_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> Dict[str, Any]: + """ + Delete a scheduled backup policy for a dedicated database. Backups already taken by the policy are kept until their retention expires. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def update_backup_storage( + self, + database_id: str, + provider: str, + bucket: str, + access_key: str, + secret_key: str, + region: Optional[str] = None, + prefix: Optional[str] = None, + endpoint: Optional[str] = None, + ) -> DedicatedDatabaseBackupStorage: + """ + Configure off-cluster backup storage for a dedicated database. Supports S3, GCS, and Azure Blob Storage destinations. Backups will be stored to the configured destination in addition to on-cluster storage. + + Parameters + ---------- + database_id : str + Database ID. + provider : str + Storage provider for off-cluster backups. Allowed values: s3 (Amazon S3 or S3-compatible), gcs (Google Cloud Storage), azure (Azure Blob Storage). + bucket : str + Storage bucket or container name. + access_key : str + Access key or client ID for authentication. + secret_key : str + Secret key or service account JSON for authentication. + region : Optional[str] + Storage region. + prefix : Optional[str] + Object key prefix for backups. + endpoint : Optional[str] + Custom endpoint for S3-compatible storage (e.g. MinIO). + Returns + ------- + DedicatedDatabaseBackupStorage + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/storage' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if provider is None: + raise AppwriteException('Missing required parameter: "provider"') + if bucket is None: + raise AppwriteException('Missing required parameter: "bucket"') + if access_key is None: + raise AppwriteException('Missing required parameter: "access_key"') + if secret_key is None: + raise AppwriteException('Missing required parameter: "secret_key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['provider'] = self._normalize_value(provider) + api_params['bucket'] = self._normalize_value(bucket) + if region is not None: + api_params['region'] = self._normalize_value(region) + if prefix is not None: + api_params['prefix'] = self._normalize_value(prefix) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + api_params['accessKey'] = self._normalize_value(access_key) + api_params['secretKey'] = self._normalize_value(secret_key) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupStorage) + + def get_backup( + self, + database_id: str, + backup_id: str, + ) -> DedicatedDatabaseBackup: + """ + Get details of a specific database backup including its status, size, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def delete_backup( + self, + database_id: str, + backup_id: str, + ) -> Dict[str, Any]: + """ + Delete a database backup. This will permanently remove the backup from storage and cannot be undone. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_branches( + self, + database_id: str, + ) -> DedicatedDatabaseBranchList: + """ + List all ephemeral branches for a dedicated database. Returns branch metadata including ID, name, namespace, and expiration time. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseBranchList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBranchList) + + def create_branch( + self, + database_id: str, + branch_id: Optional[str] = None, + ttl: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create an ephemeral database branch from the primary via PVC snapshot. The branch is a full copy of the database at the current point in time, useful for testing schema migrations or running experiments without affecting production data. Branches expire after the configured TTL (default 24 hours). The branch is created asynchronously. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : Optional[str] + Branch ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + ttl : Optional[float] + Time-to-live in seconds before the branch expires. Min 300 (5 min), max 604800 (7 days). Default: 86400 (24h). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if branch_id is not None: + api_params['branchId'] = self._normalize_value(branch_id) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete_branch( + self, + database_id: str, + branch_id: str, + ) -> DedicatedDatabase: + """ + Delete an ephemeral database branch. This removes the branch namespace, its PVC, and the associated VolumeSnapshot. The deletion runs asynchronously and is irreversible. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : str + Branch ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/branches/{branchId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if branch_id is None: + raise AppwriteException('Missing required parameter: "branch_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{branchId}', str(self._normalize_value(branch_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_credentials( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Rotate the primary connection credentials for a dedicated database. Generates a new password and updates the database atomically. Previous credentials stop working immediately. Returns the database with a refreshed connection string carrying the new password. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/credentials' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_execution( + self, + database_id: str, + sql: str, + bindings: Optional[Dict[str, Any]] = None, + timeout_seconds: Optional[float] = None, + ) -> DedicatedDatabaseExecution: + """ + Execute SQL through the console-facing Cloud endpoint. Cloud proxies through the edge platform to the per-database SQL API sidecar. Application traffic should bypass cloud entirely and POST directly to the per-database hostname: `https://db-{project}-{db}.{region}.appwrite.center/v1/sql/executions` with an `X-Appwrite-Key` header — that path scales to the whole DB fleet without a per-query cloud round-trip. The statement type must be on the database's configured allow-list. Use bound parameters for any user-supplied values — the API does not interpolate raw strings. + + Parameters + ---------- + database_id : str + Database ID. + sql : str + SQL statement to execute. Exactly one statement per request. + bindings : Optional[Dict[str, Any]] + Optional bound parameters. Pass either a positional list or a name => value map matching the placeholder style used in the SQL. + timeout_seconds : Optional[float] + Per-call execution timeout override. Must be less than or equal to the database's configured sqlApiTimeoutSeconds. + Returns + ------- + DedicatedDatabaseExecution + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/executions' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if sql is None: + raise AppwriteException('Missing required parameter: "sql"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['sql'] = self._normalize_value(sql) + if bindings is not None: + api_params['bindings'] = self._normalize_value(bindings) + if timeout_seconds is not None: + api_params['timeoutSeconds'] = self._normalize_value(timeout_seconds) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseExecution) + + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_maintenance( + self, + database_id: str, + day: str, + hour_utc: float, + ) -> DedicatedDatabase: + """ + Update the maintenance window for a dedicated database. Maintenance operations like minor version upgrades will be performed during this window. + + Parameters + ---------- + database_id : str + Database ID. + day : str + Day of the week for the maintenance window. Allowed values: sun, mon, tue, wed, thu, fri, sat. + hour_utc : float + Hour in UTC (0-23) for maintenance window start. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/maintenance' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if day is None: + raise AppwriteException('Missing required parameter: "day"') + if hour_utc is None: + raise AppwriteException('Missing required parameter: "hour_utc"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['day'] = self._normalize_value(day) + api_params['hourUtc'] = self._normalize_value(hour_utc) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_migration( + self, + database_id: str, + target_type: str, + specification: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Migrate a database between shared and dedicated types. Shared to dedicated provisions an always-on dedicated instance; dedicated to shared converts to a serverless instance that scales to zero when idle. Data is copied to the target with a brief read-only window during cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_type : str + Target database type to migrate to. Allowed values: shared (serverless, scales to zero when idle), dedicated (always-on with persistent resources). + specification : Optional[str] + Target specification to provision when migrating to dedicated. Ignored for shared. Defaults to the database's current specification. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/migrations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_type is None: + raise AppwriteException('Missing required parameter: "target_type"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetType'] = self._normalize_value(target_type) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_pitr( + self, + database_id: str, + ) -> DedicatedDatabasePITRWindows: + """ + Get available point-in-time recovery windows for a dedicated database. Returns the earliest and latest recovery points. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabasePITRWindows + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/pitr' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePITRWindows) + + def get_pooler( + self, + database_id: str, + ) -> DedicatedDatabasePooler: + """ + Get the connection pooler configuration for a dedicated database. Returns pooler mode, max connections, and pool size settings. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabasePooler + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/pooler' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePooler) + + def update_pooler( + self, + database_id: str, + mode: Optional[str] = None, + max_connections: Optional[float] = None, + default_pool_size: Optional[float] = None, + read_write_splitting: Optional[bool] = None, + pooler_cpu_request: Optional[str] = None, + pooler_cpu_limit: Optional[str] = None, + pooler_memory_request: Optional[str] = None, + pooler_memory_limit: Optional[str] = None, + ) -> DedicatedDatabasePooler: + """ + Update the connection pooler configuration for a dedicated database. Configure pool mode, max connections, and pool sizes. + + Parameters + ---------- + database_id : str + Database ID. + mode : Optional[str] + Connection pool mode. Allowed values: transaction, session. Transaction mode returns connections to the pool after each transaction; session mode holds connections for the entire session lifetime. + max_connections : Optional[float] + Client-connection ceiling the pooler accepts. Supported on MySQL and MariaDB only; the PostgreSQL pooler has no client cap, so set networkMaxConnections on the database instead. + default_pool_size : Optional[float] + Default pool size per user. + read_write_splitting : Optional[bool] + Route SELECTs to HA replicas, writes and locked reads to the primary. Defaults to true when HA is enabled. + pooler_cpu_request : Optional[str] + Pooler sidecar CPU request override (Kubernetes quantity, e.g. "250m" or "1"). Leave null for the proportional default (5% of DB CPU, floor 100m). + pooler_cpu_limit : Optional[str] + Pooler sidecar CPU limit override (Kubernetes quantity, e.g. "500m" or "1"). Leave null for the proportional default (10% of DB CPU, floor 200m). Changing this field rolls the database pod. + pooler_memory_request : Optional[str] + Pooler sidecar memory request override (Kubernetes quantity, e.g. "128Mi" or "1Gi"). Leave null for the proportional default (7.5% of DB memory, floor 64Mi). + pooler_memory_limit : Optional[str] + Pooler sidecar memory limit override (Kubernetes quantity, e.g. "256Mi" or "1Gi"). Leave null for the proportional default (15% of DB memory, floor 128Mi). Changing this field rolls the database pod. + Returns + ------- + DedicatedDatabasePooler + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/pooler' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if mode is not None: + api_params['mode'] = self._normalize_value(mode) + if max_connections is not None: + api_params['maxConnections'] = self._normalize_value(max_connections) + if default_pool_size is not None: + api_params['defaultPoolSize'] = self._normalize_value(default_pool_size) + if read_write_splitting is not None: + api_params['readWriteSplitting'] = self._normalize_value(read_write_splitting) + if pooler_cpu_request is not None: + api_params['poolerCpuRequest'] = self._normalize_value(pooler_cpu_request) + if pooler_cpu_limit is not None: + api_params['poolerCpuLimit'] = self._normalize_value(pooler_cpu_limit) + if pooler_memory_request is not None: + api_params['poolerMemoryRequest'] = self._normalize_value(pooler_memory_request) + if pooler_memory_limit is not None: + api_params['poolerMemoryLimit'] = self._normalize_value(pooler_memory_limit) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePooler) + + def get_replicas( + self, + database_id: str, + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + def list_restorations( + self, + database_id: str, + status: Optional[str] = None, + type: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseRestorationList: + """ + List all restorations for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by restoration status. + type : Optional[str] + Filter by restoration type. + limit : Optional[float] + Maximum number of restorations to return. + offset : Optional[float] + Number of restorations to skip. + Returns + ------- + DedicatedDatabaseRestorationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if type is not None: + api_params['type'] = self._normalize_value(type) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestorationList) + + def create_restoration( + self, + database_id: str, + type: Optional[str] = None, + backup_id: Optional[str] = None, + target_database_id: Optional[str] = None, + target_time: Optional[str] = None, + ) -> DedicatedDatabaseRestoration: + """ + Restore a database from a backup or to a specific point in time (PITR). For backup restoration, provide a backupId. For PITR, provide a targetTime as an ISO 8601 datetime. PITR requires the database to have PITR enabled and is only available for enterprise databases. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Restoration type. Allowed values: backup, pitr. Use "backup" to restore from a specific backup, or "pitr" for point-in-time recovery. + backup_id : Optional[str] + Backup ID to restore from (required for backup type). + target_database_id : Optional[str] + Existing database ID to restore into. The target must be distinct, ready, and use the same engine and version. + target_time : Optional[str] + Target time for PITR (required for pitr type) as an [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) datetime. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + if backup_id is not None: + api_params['backupId'] = self._normalize_value(backup_id) + if target_database_id is not None: + api_params['targetDatabaseId'] = self._normalize_value(target_database_id) + if target_time is not None: + api_params['targetTime'] = self._normalize_value(target_time) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_restoration( + self, + database_id: str, + restoration_id: str, + ) -> DedicatedDatabaseRestoration: + """ + Get details of a specific database restoration including its status, type, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + restoration_id : str + Restoration ID. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/restorations/{restorationId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if restoration_id is None: + raise AppwriteException('Missing required parameter: "restoration_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{restorationId}', str(self._normalize_value(restoration_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_status( + self, + database_id: str, + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseStatus) + + def create_upgrade( + self, + database_id: str, + target_version: str, + ) -> DedicatedDatabase: + """ + Upgrade a dedicated database to a new engine version. Uses blue-green deployment for zero-downtime cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_version : str + Target engine version to upgrade to. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/mysql/{databaseId}/upgrades' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_version is None: + raise AppwriteException('Missing required parameter: "target_version"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetVersion'] = self._normalize_value(target_version) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) diff --git a/appwrite/services/oauth2.py b/appwrite/services/oauth2.py index cf7f0bc6..31489fef 100644 --- a/appwrite/services/oauth2.py +++ b/appwrite/services/oauth2.py @@ -13,6 +13,7 @@ from ..models.oauth2_reject import Oauth2Reject from ..models.oauth2_token import Oauth2Token + class Oauth2(Service): def __init__(self, client) -> None: @@ -22,7 +23,7 @@ def approve( self, grant_id: str, authorization_details: Optional[str] = None, - scope: Optional[str] = None + scope: Optional[str] = None, ) -> Oauth2Approve: """ Approve an OAuth2 grant after the user gives consent. Returns the `redirectUrl` the end user should be sent to. The consent screen may optionally pass enriched `authorization_details` to record the concrete resources the user selected. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. @@ -35,12 +36,11 @@ def approve( Enriched `authorization_details` the user consented to, replacing what the client requested. Each entry must use a `type` the project accepts. Optional; omit to keep the originally requested details. scope : Optional[str] Space-separated scopes the user consented to. Must be a subset of the scopes originally requested; identity scopes such as `openid` are always retained. Optional; omit to keep the originally requested scopes. - Returns ------- Oauth2Approve API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -51,23 +51,25 @@ def approve( api_params = {} if grant_id is None: raise AppwriteException('Missing required parameter: "grant_id"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['grant_id'] = self._normalize_value(grant_id) if authorization_details is not None: api_params['authorization_details'] = self._normalize_value(authorization_details) if scope is not None: api_params['scope'] = self._normalize_value(scope) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Approve) - def authorize( self, client_id: Optional[str] = None, @@ -83,7 +85,7 @@ def authorize( authorization_details: Optional[str] = None, resource: Optional[str] = None, audience: Optional[str] = None, - request_uri: Optional[str] = None + request_uri: Optional[str] = None, ) -> Oauth2Authorize: """ Begin the OAuth2 authorization flow. When called without a session, the user is redirected to the consent screen without grant ID. When called with a session, the redirect URL includes param for grant ID. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. @@ -118,12 +120,11 @@ def authorize( Compatibility alias for a single OAuth2 resource indicator URI. request_uri : Optional[str] OAuth2 authorization request handle returned by the pushed authorization request endpoint. - Returns ------- Oauth2Authorize API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -133,7 +134,6 @@ def authorize( api_path = '/oauth2/{project_id}/authorize' api_params = {} api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - if client_id is not None: api_params['client_id'] = self._normalize_value(client_id) if redirect_uri is not None: @@ -163,13 +163,17 @@ def authorize( if request_uri is not None: api_params['request_uri'] = self._normalize_value(request_uri) - response = self.client.call('get', api_path, { - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Authorize) - def authorize_post( self, client_id: Optional[str] = None, @@ -185,7 +189,7 @@ def authorize_post( authorization_details: Optional[str] = None, resource: Optional[str] = None, audience: Optional[str] = None, - request_uri: Optional[str] = None + request_uri: Optional[str] = None, ) -> Oauth2Authorize: """ Begin the OAuth2 authorization flow. When called without a session, the user is redirected to the consent screen without grant ID. When called with a session, the redirect URL includes param for grant ID. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. @@ -220,12 +224,11 @@ def authorize_post( Compatibility alias for a single OAuth2 resource indicator URI. request_uri : Optional[str] OAuth2 authorization request handle returned by the pushed authorization request endpoint. - Returns ------- Oauth2Authorize API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -235,7 +238,6 @@ def authorize_post( api_path = '/oauth2/{project_id}/authorize' api_params = {} api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - if client_id is not None: api_params['client_id'] = self._normalize_value(client_id) if redirect_uri is not None: @@ -265,21 +267,25 @@ def authorize_post( if request_uri is not None: api_params['request_uri'] = self._normalize_value(request_uri) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Authorize) - def create_device_authorization( self, client_id: Optional[str] = None, scope: Optional[str] = None, authorization_details: Optional[str] = None, resource: Optional[str] = None, - audience: Optional[str] = None + audience: Optional[str] = None, ) -> Oauth2DeviceAuthorization: """ Start the OAuth2 Device Authorization Grant. Returns the device code, user code, verification URL, expiration, and polling interval. @@ -296,12 +302,11 @@ def create_device_authorization( RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. audience : Optional[str] Compatibility alias for a single OAuth2 resource indicator URI. - Returns ------- Oauth2DeviceAuthorization API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -311,7 +316,6 @@ def create_device_authorization( api_path = '/oauth2/{project_id}/device_authorization' api_params = {} api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - if client_id is not None: api_params['client_id'] = self._normalize_value(client_id) if scope is not None: @@ -323,17 +327,21 @@ def create_device_authorization( if audience is not None: api_params['audience'] = self._normalize_value(audience) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2DeviceAuthorization) - def create_grant( self, - user_code: str + user_code: str, ) -> Oauth2Grant: """ Exchange a device flow user code for an OAuth2 grant. The authenticated user is bound to the pending grant. Pass the returned grant ID to the get grant endpoint to render the consent screen, then to the approve or reject endpoint to complete the flow. @@ -342,12 +350,11 @@ def create_grant( ---------- user_code : str User code displayed on the device. - Returns ------- Oauth2Grant API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -358,22 +365,24 @@ def create_grant( api_params = {} if user_code is None: raise AppwriteException('Missing required parameter: "user_code"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['user_code'] = self._normalize_value(user_code) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Grant) - def get_grant( self, - grant_id: str + grant_id: str, ) -> Oauth2Grant: """ Get an OAuth2 grant by its ID. Used by the consent screen to display the details of the authorization the user is being asked to approve. A grant can only be read by the user it belongs to, or by server SDK. @@ -382,12 +391,11 @@ def get_grant( ---------- grant_id : str Grant ID made during authorization, provided to consent screen in URL search params. - Returns ------- Oauth2Grant API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -398,23 +406,25 @@ def get_grant( api_params = {} if grant_id is None: raise AppwriteException('Missing required parameter: "grant_id"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) api_path = api_path.replace('{grant_id}', str(self._normalize_value(grant_id))) - - response = self.client.call('get', api_path, { - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Grant) - def list_organizations( self, limit: Optional[float] = None, offset: Optional[float] = None, - search: Optional[str] = None + search: Optional[str] = None, ) -> Oauth2OrganizationList: """ List the organizations the OAuth2 access token can access. Resolves the token's `organization` authorization details, expanding the `*` wildcard into the concrete set of organizations the user can see. @@ -427,12 +437,11 @@ def list_organizations( Number of organizations to skip before returning results. Used for pagination. search : Optional[str] Search term to filter your list results. Max length: 256 chars. - Returns ------- Oauth2OrganizationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -442,7 +451,6 @@ def list_organizations( api_path = '/oauth2/{project_id}/organizations' api_params = {} api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - if limit is not None: api_params['limit'] = self._normalize_value(limit) if offset is not None: @@ -450,13 +458,17 @@ def list_organizations( if search is not None: api_params['search'] = self._normalize_value(search) - response = self.client.call('get', api_path, { - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2OrganizationList) - def create_par( self, client_id: str, @@ -471,7 +483,7 @@ def create_par( max_age: Optional[float] = None, authorization_details: Optional[str] = None, resource: Optional[str] = None, - audience: Optional[str] = None + audience: Optional[str] = None, ) -> Oauth2PAR: """ Store an OAuth2 authorization request server-side and receive a short-lived request_uri handle for the authorize endpoint. @@ -504,12 +516,11 @@ def create_par( RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. audience : Optional[str] Compatibility alias for a single OAuth2 resource indicator URI. - Returns ------- Oauth2PAR API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -520,15 +531,11 @@ def create_par( api_params = {} if client_id is None: raise AppwriteException('Missing required parameter: "client_id"') - if redirect_uri is None: raise AppwriteException('Missing required parameter: "redirect_uri"') - if response_type is None: raise AppwriteException('Missing required parameter: "response_type"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['client_id'] = self._normalize_value(client_id) api_params['redirect_uri'] = self._normalize_value(redirect_uri) api_params['response_type'] = self._normalize_value(response_type) @@ -553,19 +560,23 @@ def create_par( if audience is not None: api_params['audience'] = self._normalize_value(audience) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2PAR) - def list_projects( self, limit: Optional[float] = None, offset: Optional[float] = None, - search: Optional[str] = None + search: Optional[str] = None, ) -> Oauth2ProjectList: """ List the projects the OAuth2 access token can access. Resolves the token's `project` authorization details, expanding the `*` wildcard into the concrete set of projects the user can see. @@ -578,12 +589,11 @@ def list_projects( Number of projects to skip before returning results. Used for pagination. search : Optional[str] Search term to filter your list results. Max length: 256 chars. - Returns ------- Oauth2ProjectList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -593,7 +603,6 @@ def list_projects( api_path = '/oauth2/{project_id}/projects' api_params = {} api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - if limit is not None: api_params['limit'] = self._normalize_value(limit) if offset is not None: @@ -601,16 +610,20 @@ def list_projects( if search is not None: api_params['search'] = self._normalize_value(search) - response = self.client.call('get', api_path, { - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2ProjectList) - def reject( self, - grant_id: str + grant_id: str, ) -> Oauth2Reject: """ Reject an OAuth2 grant when the user denies consent. Returns the `redirectUrl` the end user should be sent to with an `access_denied` error. You can pass Accept header of `application/json` to receive a JSON response instead of a redirect. @@ -619,12 +632,11 @@ def reject( ---------- grant_id : str Grant ID made during authorization, provided to consent screen in URL search params. - Returns ------- Oauth2Reject API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -635,25 +647,27 @@ def reject( api_params = {} if grant_id is None: raise AppwriteException('Missing required parameter: "grant_id"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['grant_id'] = self._normalize_value(grant_id) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Reject) - def revoke( self, token: str, token_type_hint: Optional[str] = None, client_id: Optional[str] = None, - client_secret: Optional[str] = None + client_secret: Optional[str] = None, ) -> Dict[str, Any]: """ Revoke an OAuth2 access token or refresh token. @@ -668,12 +682,11 @@ def revoke( OAuth2 client ID. Either a registered app ID or an HTTPS client ID metadata document URL. client_secret : Optional[str] OAuth2 client secret. Required for confidential apps; omitted for public apps. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -684,9 +697,7 @@ def revoke( api_params = {} if token is None: raise AppwriteException('Missing required parameter: "token"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['token'] = self._normalize_value(token) if token_type_hint is not None: api_params['token_type_hint'] = self._normalize_value(token_type_hint) @@ -695,14 +706,18 @@ def revoke( if client_secret is not None: api_params['client_secret'] = self._normalize_value(client_secret) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def create_token( self, grant_type: str, @@ -714,7 +729,7 @@ def create_token( code_verifier: Optional[str] = None, redirect_uri: Optional[str] = None, resource: Optional[str] = None, - audience: Optional[str] = None + audience: Optional[str] = None, ) -> Oauth2Token: """ Exchange an OAuth2 authorization code, refresh token, or device code for access and refresh tokens. @@ -741,12 +756,11 @@ def create_token( RFC 8707 resource indicator URI or URI list. Each value must be an absolute URI without a fragment. audience : Optional[str] Compatibility alias for a single OAuth2 resource indicator URI. - Returns ------- Oauth2Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -757,9 +771,7 @@ def create_token( api_params = {} if grant_type is None: raise AppwriteException('Missing required parameter: "grant_type"') - api_path = api_path.replace('{project_id}', str(self._normalize_value(self.client.get_config('project')))) - api_params['grant_type'] = self._normalize_value(grant_type) if code is not None: api_params['code'] = self._normalize_value(code) @@ -780,10 +792,14 @@ def create_token( if audience is not None: api_params['audience'] = self._normalize_value(audience) - response = self.client.call('post', api_path, { - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Oauth2Token) - diff --git a/appwrite/services/organization.py b/appwrite/services/organization.py index 6ea8aa89..aa7eed39 100644 --- a/appwrite/services/organization.py +++ b/appwrite/services/organization.py @@ -17,6 +17,7 @@ T = TypeVar('T') + class Organization(Service): def __init__(self, client) -> None: @@ -24,22 +25,21 @@ def __init__(self, client) -> None: def get( self, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> OrganizationModel[T]: """ Get the current organization. Parameters ---------- - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- OrganizationModel[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -49,18 +49,22 @@ def get( api_path = '/organization' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return OrganizationModel.with_data(response, model_type) - def update( self, name: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> OrganizationModel[T]: """ Update the current organization's name. @@ -69,15 +73,14 @@ def update( ---------- name : str New organization name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- OrganizationModel[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -88,30 +91,31 @@ def update( api_params = {} if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['name'] = self._normalize_value(name) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return OrganizationModel.with_data(response, model_type) - def delete( - self + self, ) -> Dict[str, Any]: """ Delete the current organization. All projects that belong to the organization are deleted as well. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -121,18 +125,22 @@ def delete( api_path = '/organization' api_params = {} - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_installations( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppInstallationList: """ List app installations on the organization. Any organization member can read installations. @@ -143,12 +151,11 @@ def list_installations( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppInstallationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -157,24 +164,27 @@ def list_installations( api_path = '/organization/installations' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallationList) - def create_installation( self, app_id: str, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, ) -> AppInstallation: """ Install an app on the organization. Only organization members with the owner role can install apps. The installation is granted the scopes the app currently requests. @@ -185,12 +195,11 @@ def create_installation( Application unique ID. authorization_details : Optional[str] Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. The Appwrite Console stores authorized project IDs here. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -201,24 +210,26 @@ def create_installation( api_params = {} if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - - api_params['appId'] = self._normalize_value(app_id) if authorization_details is not None: api_params['authorizationDetails'] = self._normalize_value(authorization_details) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def get_installation( self, - installation_id: str + installation_id: str, ) -> AppInstallation: """ Get an app installation on the organization by its unique ID. Any organization member can read installations. @@ -227,12 +238,11 @@ def get_installation( ---------- installation_id : str Installation unique ID. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -243,22 +253,24 @@ def get_installation( api_params = {} if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def update_installation( self, installation_id: str, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, ) -> AppInstallation: """ Update an app installation on the organization. Only organization members with the owner role can update installations. The installation's granted scopes are refreshed to the scopes the app currently requests; previously issued installation access tokens are revoked. @@ -269,12 +281,11 @@ def update_installation( Installation unique ID. authorization_details : Optional[str] Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. Omit to keep the current value. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -285,24 +296,26 @@ def update_installation( api_params = {} if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - if authorization_details is not None: api_params['authorizationDetails'] = self._normalize_value(authorization_details) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def delete_installation( self, - installation_id: str + installation_id: str, ) -> Dict[str, Any]: """ Uninstall an app from the organization by its installation ID. Only organization members with the owner role can remove installations. Previously issued installation access tokens are revoked. @@ -311,12 +324,11 @@ def delete_installation( ---------- installation_id : str Installation unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -327,23 +339,25 @@ def delete_installation( api_params = {} if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_keys( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> KeyList: """ Get a list of all API keys from the current organization. @@ -354,12 +368,11 @@ def list_keys( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: expire, accessedAt, name, scopes total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- KeyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -368,26 +381,29 @@ def list_keys( api_path = '/organization/keys' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=KeyList) - def create_key( self, key_id: str, name: str, scopes: List[OrganizationKeyScopes], - expire: Optional[str] = None + expire: Optional[str] = None, ) -> Key: """ Create a new organization API key. @@ -402,12 +418,11 @@ def create_key( Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. - Returns ------- Key API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -418,32 +433,32 @@ def create_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if scopes is None: raise AppwriteException('Missing required parameter: "scopes"') - - api_params['keyId'] = self._normalize_value(key_id) api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Key) - def get_key( self, - key_id: str + key_id: str, ) -> Key: """ Get a key by its unique ID. This endpoint returns details about a specific API key in your organization including its scopes. @@ -452,12 +467,11 @@ def get_key( ---------- key_id : str Key unique ID. - Returns ------- Key API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -468,24 +482,26 @@ def get_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Key) - def update_key( self, key_id: str, name: str, scopes: List[OrganizationKeyScopes], - expire: Optional[str] = None + expire: Optional[str] = None, ) -> Key: """ Update a key by its unique ID. Use this endpoint to update the name, scopes, or expiration time of an API key. @@ -500,12 +516,11 @@ def update_key( Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. - Returns ------- Key API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -516,32 +531,32 @@ def update_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if scopes is None: raise AppwriteException('Missing required parameter: "scopes"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Key) - def delete_key( self, - key_id: str + key_id: str, ) -> Dict[str, Any]: """ Delete a key by its unique ID. Once deleted, the key can no longer be used to authenticate API calls. @@ -550,12 +565,11 @@ def delete_key( ---------- key_id : str Key unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -566,23 +580,25 @@ def delete_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_memberships( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> MembershipList: """ Get a list of all memberships from the current organization. @@ -595,12 +611,11 @@ def list_memberships( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- MembershipList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -609,7 +624,6 @@ def list_memberships( api_path = '/organization/memberships' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -617,14 +631,18 @@ def list_memberships( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MembershipList) - def create_membership( self, roles: List[str], @@ -632,7 +650,7 @@ def create_membership( user_id: Optional[str] = None, phone: Optional[str] = None, url: Optional[str] = None, - name: Optional[str] = None + name: Optional[str] = None, ) -> Membership: """ Invite a new member to join the current organization. An email with a link to join the organization will be sent to the new member's email address. If member doesn't exist in the project it will be automatically created. @@ -651,12 +669,11 @@ def create_membership( URL to redirect the user back to your app from the invitation email. This parameter is not required when an API key is supplied. name : Optional[str] Name of the new organization member. Max length: 128 chars. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -667,8 +684,6 @@ def create_membership( api_params = {} if roles is None: raise AppwriteException('Missing required parameter: "roles"') - - if email is not None: api_params['email'] = self._normalize_value(email) if user_id is not None: @@ -681,18 +696,22 @@ def create_membership( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def get_membership( self, - membership_id: str + membership_id: str, ) -> Membership: """ Get a membership from the current organization by its unique ID. @@ -701,12 +720,11 @@ def get_membership( ---------- membership_id : str Membership ID. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -717,22 +735,24 @@ def get_membership( api_params = {} if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def update_membership( self, membership_id: str, - roles: List[str] + roles: List[str], ) -> Membership: """ Modify the roles of a member in the current organization. @@ -743,12 +763,11 @@ def update_membership( Membership ID. roles : List[str] An array of strings. Use this param to set the user's roles in the organization. A role can be any string. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). Maximum of 100 roles are allowed, each 81 characters long. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -759,26 +778,27 @@ def update_membership( api_params = {} if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - if roles is None: raise AppwriteException('Missing required parameter: "roles"') - api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - api_params['roles'] = self._normalize_value(roles) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def delete_membership( self, - membership_id: str + membership_id: str, ) -> Dict[str, Any]: """ Remove a member from the current organization. The member is removed whether they accepted the invitation or not; a pending invitation is revoked. @@ -787,12 +807,11 @@ def delete_membership( ---------- membership_id : str Membership ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -803,23 +822,25 @@ def delete_membership( api_params = {} if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_projects( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ProjectList: """ Get a list of all projects. You can use the query params to filter your results. @@ -832,12 +853,11 @@ def list_projects( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ProjectList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -846,7 +866,6 @@ def list_projects( api_path = '/organization/projects' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -854,19 +873,23 @@ def list_projects( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectList) - def create_project( self, project_id: str, name: str, - region: Optional[Region] = None + region: Optional[Region] = None, ) -> Project: """ Create a new project. @@ -879,12 +902,11 @@ def create_project( Project name. Max length: 128 chars. region : Optional[Region] Project Region. - Returns ------- Project API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -895,28 +917,29 @@ def create_project( api_params = {} if project_id is None: raise AppwriteException('Missing required parameter: "project_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['projectId'] = self._normalize_value(project_id) api_params['name'] = self._normalize_value(name) if region is not None: api_params['region'] = self._normalize_value(region) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Project) - def get_project( self, - project_id: str + project_id: str, ) -> Project: """ Get a project. @@ -925,12 +948,11 @@ def get_project( ---------- project_id : str Project unique ID. - Returns ------- Project API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -941,21 +963,23 @@ def get_project( api_params = {} if project_id is None: raise AppwriteException('Missing required parameter: "project_id"') - api_path = api_path.replace('{projectId}', str(self._normalize_value(project_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + }, + api_params, + ) return self._parse_response(response, model=Project) - def update_project( self, project_id: str, - name: str + name: str, ) -> Project: """ Update a project by its unique ID. @@ -966,12 +990,11 @@ def update_project( Project unique ID. name : str Project name. Max length: 128 chars. - Returns ------- Project API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -982,26 +1005,27 @@ def update_project( api_params = {} if project_id is None: raise AppwriteException('Missing required parameter: "project_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{projectId}', str(self._normalize_value(project_id))) - api_params['name'] = self._normalize_value(name) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Project) - def delete_project( self, - project_id: str + project_id: str, ) -> Dict[str, Any]: """ Delete a project by its unique ID. @@ -1010,12 +1034,11 @@ def delete_project( ---------- project_id : str Project unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1026,14 +1049,16 @@ def delete_project( api_params = {} if project_id is None: raise AppwriteException('Missing required parameter: "project_id"') - api_path = api_path.replace('{projectId}', str(self._normalize_value(project_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/postgresql.py b/appwrite/services/postgresql.py new file mode 100644 index 00000000..3c1bdb7f --- /dev/null +++ b/appwrite/services/postgresql.py @@ -0,0 +1,2007 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..models.dedicated_database_list import DedicatedDatabaseList +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from ..models.dedicated_database_backup_list import DedicatedDatabaseBackupList +from ..models.dedicated_database_backup import DedicatedDatabaseBackup +from ..models.backup_policy_list import BackupPolicyList +from ..models.backup_policy import BackupPolicy +from ..models.dedicated_database_backup_storage import DedicatedDatabaseBackupStorage +from ..models.dedicated_database_branch_list import DedicatedDatabaseBranchList +from ..models.dedicated_database_execution import DedicatedDatabaseExecution +from ..models.dedicated_database_extensions import DedicatedDatabaseExtensions +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList +from ..models.dedicated_database_pitr_windows import DedicatedDatabasePITRWindows +from ..models.dedicated_database_pooler import DedicatedDatabasePooler +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.dedicated_database_restoration_list import DedicatedDatabaseRestorationList +from ..models.dedicated_database_restoration import DedicatedDatabaseRestoration +from ..models.database_status import DatabaseStatus + + +class Postgresql(Service): + + def __init__(self, client) -> None: + super(Postgresql, self).__init__(client) + + def list( + self, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseList: + """ + List all dedicated databases. Results support pagination. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings. + Returns + ------- + DedicatedDatabaseList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseList) + + def create( + self, + database_id: str, + name: str, + version: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create a new dedicated database with the chosen engine and configuration. Status will be 'provisioning' until the database is ready. + + Parameters + ---------- + database_id : str + Database ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Database display name. Max length: 128 chars. + version : Optional[str] + Database engine version. Defaults to latest for selected engine. + specification : Optional[str] + Specification identifier. Drives the allocated CPU, memory, storage, storage class, and connection ceiling. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds. + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes of inactivity before container scales to zero. + pitr : Optional[bool] + Enable point-in-time recovery (PITR). Continuously archives changes so the database can be restored to any moment within the retention window. + pitr_retention_days : Optional[float] + Number of days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_params['databaseId'] = self._normalize_value(database_id) + api_params['name'] = self._normalize_value(name) + if version is not None: + api_params['version'] = self._normalize_value(version) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_specifications( + self, + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/specifications' + api_params = {} + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def get( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Get a dedicated database by its unique ID. Returns the database configuration and current status. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update( + self, + database_id: str, + name: Optional[str] = None, + status: Optional[str] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + network_idle_timeout_seconds: Optional[float] = None, + network_ip_allowlist: Optional[List[str]] = None, + idle_timeout_minutes: Optional[float] = None, + pitr: Optional[bool] = None, + pitr_retention_days: Optional[float] = None, + storage_autoscaling: Optional[bool] = None, + storage_autoscaling_threshold_percent: Optional[float] = None, + storage_autoscaling_max_gb: Optional[float] = None, + metrics_trace_sample_rate: Optional[float] = None, + metrics_slow_query_log_threshold_ms: Optional[float] = None, + sql_api_enabled: Optional[bool] = None, + sql_api_allowed_statements: Optional[List[str]] = None, + sql_api_max_rows: Optional[float] = None, + sql_api_max_bytes: Optional[float] = None, + sql_api_timeout_seconds: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Update a dedicated database configuration. All changes are applied with zero downtime. Specification changes (cpu, memory, storage) are handled via rolling cutover. Storage expansion is done online. All other settings are applied in-place. + + Parameters + ---------- + database_id : str + Database ID. + name : Optional[str] + Database display name. + status : Optional[str] + Database status. Allowed values: ready, paused, inactive. Set to "paused" to pause, "ready" to resume (also recovers a failed database whose infrastructure is healthy), or "inactive" to spin down a shared-pool database. + specification : Optional[str] + Specification. Changes cpu, memory, storage, connection ceiling, and node pool based on specification config. Resource changes are applied via rolling cutover with zero downtime. + replicas : Optional[float] + Number of high availability replicas (0-5). High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode preference. Allowed values: async, sync, quorum. + network_idle_timeout_seconds : Optional[float] + Connection idle timeout in seconds (60-86400). + network_ip_allowlist : Optional[List[str]] + IP addresses/CIDR ranges allowed to connect. + idle_timeout_minutes : Optional[float] + Minutes before container scales to zero. + pitr : Optional[bool] + Enable or disable point-in-time recovery (PITR). + pitr_retention_days : Optional[float] + Days to retain PITR data. + storage_autoscaling : Optional[bool] + Enable automatic storage expansion when usage exceeds threshold. + storage_autoscaling_threshold_percent : Optional[float] + Storage usage percentage (50-95) that triggers automatic expansion. + storage_autoscaling_max_gb : Optional[float] + Maximum storage size in GB for autoscaling. 0 means no limit. + metrics_trace_sample_rate : Optional[float] + Fraction of queries to trace (0.0–1.0). Forwarded to the sidecar. + metrics_slow_query_log_threshold_ms : Optional[float] + Threshold in ms above which queries are logged as slow. Forwarded to the sidecar. + sql_api_enabled : Optional[bool] + Enable the SQL API sidecar for this database. + sql_api_allowed_statements : Optional[List[str]] + Statement types the SQL API accepts. Allowed values: SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, DROP, TRUNCATE, GRANT, REVOKE. + sql_api_max_rows : Optional[float] + Maximum rows returned per SQL API execution (1-1000000). + sql_api_max_bytes : Optional[float] + Maximum serialised SQL API result payload in bytes (1024-104857600). + sql_api_timeout_seconds : Optional[float] + Per-call SQL API execution timeout in seconds (1-300). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if status is not None: + api_params['status'] = self._normalize_value(status) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + if network_idle_timeout_seconds is not None: + api_params['networkIdleTimeoutSeconds'] = self._normalize_value(network_idle_timeout_seconds) + if network_ip_allowlist is not None: + api_params['networkIPAllowlist'] = self._normalize_value(network_ip_allowlist) + if idle_timeout_minutes is not None: + api_params['idleTimeoutMinutes'] = self._normalize_value(idle_timeout_minutes) + if pitr is not None: + api_params['pitr'] = self._normalize_value(pitr) + if pitr_retention_days is not None: + api_params['pitrRetentionDays'] = self._normalize_value(pitr_retention_days) + if storage_autoscaling is not None: + api_params['storageAutoscaling'] = self._normalize_value(storage_autoscaling) + if storage_autoscaling_threshold_percent is not None: + api_params['storageAutoscalingThresholdPercent'] = self._normalize_value( + storage_autoscaling_threshold_percent, + ) + if storage_autoscaling_max_gb is not None: + api_params['storageAutoscalingMaxGb'] = self._normalize_value(storage_autoscaling_max_gb) + if metrics_trace_sample_rate is not None: + api_params['metricsTraceSampleRate'] = self._normalize_value(metrics_trace_sample_rate) + if metrics_slow_query_log_threshold_ms is not None: + api_params['metricsSlowQueryLogThresholdMs'] = self._normalize_value(metrics_slow_query_log_threshold_ms) + if sql_api_enabled is not None: + api_params['sqlApiEnabled'] = self._normalize_value(sql_api_enabled) + if sql_api_allowed_statements is not None: + api_params['sqlApiAllowedStatements'] = self._normalize_value(sql_api_allowed_statements) + if sql_api_max_rows is not None: + api_params['sqlApiMaxRows'] = self._normalize_value(sql_api_max_rows) + if sql_api_max_bytes is not None: + api_params['sqlApiMaxBytes'] = self._normalize_value(sql_api_max_bytes) + if sql_api_timeout_seconds is not None: + api_params['sqlApiTimeoutSeconds'] = self._normalize_value(sql_api_timeout_seconds) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete( + self, + database_id: str, + ) -> Dict[str, Any]: + """ + Delete a dedicated database. This action is irreversible. The database status will be set to 'deleting' and all resources will be cleaned up. Deletion is allowed from any state, and repeating the call re-dispatches the cleanup. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_backups( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> DedicatedDatabaseBackupList: + """ + List all backups for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: status, type, databaseId + Returns + ------- + DedicatedDatabaseBackupList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupList) + + def create_backup( + self, + database_id: str, + type: Optional[str] = None, + ) -> DedicatedDatabaseBackup: + """ + Create a manual backup of a dedicated database. The backup will be created asynchronously and its status can be checked via the get backup endpoint. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Backup type: full or incremental. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def list_backup_policies( + self, + database_id: str, + queries: Optional[List[str]] = None, + ) -> BackupPolicyList: + """ + List scheduled backup policies for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. + Returns + ------- + BackupPolicyList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicyList) + + def create_backup_policy( + self, + database_id: str, + policy_id: str, + name: str, + schedule: str, + retention: float, + type: Optional[str] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Create a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Policy name. Max length: 128 chars. + schedule : str + Schedule CRON syntax. + retention : float + Days to keep backups before deletion. + type : Optional[str] + Backup type: full or incremental. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/policies' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + if schedule is None: + raise AppwriteException('Missing required parameter: "schedule"') + if retention is None: + raise AppwriteException('Missing required parameter: "retention"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['policyId'] = self._normalize_value(policy_id) + api_params['name'] = self._normalize_value(name) + api_params['schedule'] = self._normalize_value(schedule) + api_params['retention'] = self._normalize_value(retention) + if type is not None: + api_params['type'] = self._normalize_value(type) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def get_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> BackupPolicy: + """ + Get a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def update_backup_policy( + self, + database_id: str, + policy_id: str, + name: Optional[str] = None, + schedule: Optional[str] = None, + retention: Optional[float] = None, + enabled: Optional[bool] = None, + ) -> BackupPolicy: + """ + Update a scheduled backup policy for a dedicated database. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + name : Optional[str] + Policy name. Max length: 128 chars. + schedule : Optional[str] + Schedule CRON syntax. + retention : Optional[float] + Days to keep backups before deletion. + enabled : Optional[bool] + Is policy enabled? When disabled, no backups will be taken. + Returns + ------- + BackupPolicy + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + if name is not None: + api_params['name'] = self._normalize_value(name) + if schedule is not None: + api_params['schedule'] = self._normalize_value(schedule) + if retention is not None: + api_params['retention'] = self._normalize_value(retention) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=BackupPolicy) + + def delete_backup_policy( + self, + database_id: str, + policy_id: str, + ) -> Dict[str, Any]: + """ + Delete a scheduled backup policy for a dedicated database. Backups already taken by the policy are kept until their retention expires. + + Parameters + ---------- + database_id : str + Database ID. + policy_id : str + Policy ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/policies/{policyId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if policy_id is None: + raise AppwriteException('Missing required parameter: "policy_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def update_backup_storage( + self, + database_id: str, + provider: str, + bucket: str, + access_key: str, + secret_key: str, + region: Optional[str] = None, + prefix: Optional[str] = None, + endpoint: Optional[str] = None, + ) -> DedicatedDatabaseBackupStorage: + """ + Configure off-cluster backup storage for a dedicated database. Supports S3, GCS, and Azure Blob Storage destinations. Backups will be stored to the configured destination in addition to on-cluster storage. + + Parameters + ---------- + database_id : str + Database ID. + provider : str + Storage provider for off-cluster backups. Allowed values: s3 (Amazon S3 or S3-compatible), gcs (Google Cloud Storage), azure (Azure Blob Storage). + bucket : str + Storage bucket or container name. + access_key : str + Access key or client ID for authentication. + secret_key : str + Secret key or service account JSON for authentication. + region : Optional[str] + Storage region. + prefix : Optional[str] + Object key prefix for backups. + endpoint : Optional[str] + Custom endpoint for S3-compatible storage (e.g. MinIO). + Returns + ------- + DedicatedDatabaseBackupStorage + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/storage' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if provider is None: + raise AppwriteException('Missing required parameter: "provider"') + if bucket is None: + raise AppwriteException('Missing required parameter: "bucket"') + if access_key is None: + raise AppwriteException('Missing required parameter: "access_key"') + if secret_key is None: + raise AppwriteException('Missing required parameter: "secret_key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['provider'] = self._normalize_value(provider) + api_params['bucket'] = self._normalize_value(bucket) + if region is not None: + api_params['region'] = self._normalize_value(region) + if prefix is not None: + api_params['prefix'] = self._normalize_value(prefix) + if endpoint is not None: + api_params['endpoint'] = self._normalize_value(endpoint) + api_params['accessKey'] = self._normalize_value(access_key) + api_params['secretKey'] = self._normalize_value(secret_key) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackupStorage) + + def get_backup( + self, + database_id: str, + backup_id: str, + ) -> DedicatedDatabaseBackup: + """ + Get details of a specific database backup including its status, size, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + DedicatedDatabaseBackup + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBackup) + + def delete_backup( + self, + database_id: str, + backup_id: str, + ) -> Dict[str, Any]: + """ + Delete a database backup. This will permanently remove the backup from storage and cannot be undone. + + Parameters + ---------- + database_id : str + Database ID. + backup_id : str + Backup ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/backups/{backupId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if backup_id is None: + raise AppwriteException('Missing required parameter: "backup_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{backupId}', str(self._normalize_value(backup_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return response + + def list_branches( + self, + database_id: str, + ) -> DedicatedDatabaseBranchList: + """ + List all ephemeral branches for a dedicated database. Returns branch metadata including ID, name, namespace, and expiration time. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseBranchList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseBranchList) + + def create_branch( + self, + database_id: str, + branch_id: Optional[str] = None, + ttl: Optional[float] = None, + ) -> DedicatedDatabase: + """ + Create an ephemeral database branch from the primary via PVC snapshot. The branch is a full copy of the database at the current point in time, useful for testing schema migrations or running experiments without affecting production data. Branches expire after the configured TTL (default 24 hours). The branch is created asynchronously. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : Optional[str] + Branch ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + ttl : Optional[float] + Time-to-live in seconds before the branch expires. Min 300 (5 min), max 604800 (7 days). Default: 86400 (24h). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/branches' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if branch_id is not None: + api_params['branchId'] = self._normalize_value(branch_id) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete_branch( + self, + database_id: str, + branch_id: str, + ) -> DedicatedDatabase: + """ + Delete an ephemeral database branch. This removes the branch namespace, its PVC, and the associated VolumeSnapshot. The deletion runs asynchronously and is irreversible. + + Parameters + ---------- + database_id : str + Database ID. + branch_id : str + Branch ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/branches/{branchId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if branch_id is None: + raise AppwriteException('Missing required parameter: "branch_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{branchId}', str(self._normalize_value(branch_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_credentials( + self, + database_id: str, + ) -> DedicatedDatabase: + """ + Rotate the primary connection credentials for a dedicated database. Generates a new password and updates the database atomically. Previous credentials stop working immediately. Returns the database with a refreshed connection string carrying the new password. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/credentials' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_execution( + self, + database_id: str, + sql: str, + bindings: Optional[Dict[str, Any]] = None, + timeout_seconds: Optional[float] = None, + ) -> DedicatedDatabaseExecution: + """ + Execute SQL through the console-facing Cloud endpoint. Cloud proxies through the edge platform to the per-database SQL API sidecar. Application traffic should bypass cloud entirely and POST directly to the per-database hostname: `https://db-{project}-{db}.{region}.appwrite.center/v1/sql/executions` with an `X-Appwrite-Key` header — that path scales to the whole DB fleet without a per-query cloud round-trip. The statement type must be on the database's configured allow-list. Use bound parameters for any user-supplied values — the API does not interpolate raw strings. + + Parameters + ---------- + database_id : str + Database ID. + sql : str + SQL statement to execute. Exactly one statement per request. + bindings : Optional[Dict[str, Any]] + Optional bound parameters. Pass either a positional list or a name => value map matching the placeholder style used in the SQL. + timeout_seconds : Optional[float] + Per-call execution timeout override. Must be less than or equal to the database's configured sqlApiTimeoutSeconds. + Returns + ------- + DedicatedDatabaseExecution + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/executions' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if sql is None: + raise AppwriteException('Missing required parameter: "sql"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['sql'] = self._normalize_value(sql) + if bindings is not None: + api_params['bindings'] = self._normalize_value(bindings) + if timeout_seconds is not None: + api_params['timeoutSeconds'] = self._normalize_value(timeout_seconds) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseExecution) + + def list_extensions( + self, + database_id: str, + ) -> DedicatedDatabaseExtensions: + """ + List installed and available extensions for a PostgreSQL database. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseExtensions + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/extensions' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseExtensions) + + def create_extension( + self, + database_id: str, + name: str, + ) -> DedicatedDatabase: + """ + Install a database extension. Only available for PostgreSQL databases. The install runs asynchronously; poll the extensions list endpoint for status. + + Parameters + ---------- + database_id : str + Database ID. + name : str + Extension name (e.g., pgvector, postgis, uuid-ossp). + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/extensions' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['name'] = self._normalize_value(name) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def delete_extension( + self, + database_id: str, + extension_name: str, + ) -> DedicatedDatabase: + """ + Uninstall a database extension from a PostgreSQL database. The uninstall runs asynchronously; poll the extensions list endpoint for status. + + Parameters + ---------- + database_id : str + Database ID. + extension_name : str + Extension name to uninstall. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/extensions/{extensionName}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if extension_name is None: + raise AppwriteException('Missing required parameter: "extension_name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{extensionName}', str(self._normalize_value(extension_name))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def update_maintenance( + self, + database_id: str, + day: str, + hour_utc: float, + ) -> DedicatedDatabase: + """ + Update the maintenance window for a dedicated database. Maintenance operations like minor version upgrades will be performed during this window. + + Parameters + ---------- + database_id : str + Database ID. + day : str + Day of the week for the maintenance window. Allowed values: sun, mon, tue, wed, thu, fri, sat. + hour_utc : float + Hour in UTC (0-23) for maintenance window start. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/maintenance' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if day is None: + raise AppwriteException('Missing required parameter: "day"') + if hour_utc is None: + raise AppwriteException('Missing required parameter: "hour_utc"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['day'] = self._normalize_value(day) + api_params['hourUtc'] = self._normalize_value(hour_utc) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def create_migration( + self, + database_id: str, + target_type: str, + specification: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Migrate a database between shared and dedicated types. Shared to dedicated provisions an always-on dedicated instance; dedicated to shared converts to a serverless instance that scales to zero when idle. Data is copied to the target with a brief read-only window during cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_type : str + Target database type to migrate to. Allowed values: shared (serverless, scales to zero when idle), dedicated (always-on with persistent resources). + specification : Optional[str] + Target specification to provision when migrating to dedicated. Ignored for shared. Defaults to the database's current specification. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/migrations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_type is None: + raise AppwriteException('Missing required parameter: "target_type"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetType'] = self._normalize_value(target_type) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_pitr( + self, + database_id: str, + ) -> DedicatedDatabasePITRWindows: + """ + Get available point-in-time recovery windows for a dedicated database. Returns the earliest and latest recovery points. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabasePITRWindows + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/pitr' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePITRWindows) + + def get_pooler( + self, + database_id: str, + ) -> DedicatedDatabasePooler: + """ + Get the connection pooler configuration for a dedicated database. Returns pooler mode, max connections, and pool size settings. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabasePooler + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/pooler' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePooler) + + def update_pooler( + self, + database_id: str, + mode: Optional[str] = None, + max_connections: Optional[float] = None, + default_pool_size: Optional[float] = None, + read_write_splitting: Optional[bool] = None, + pooler_cpu_request: Optional[str] = None, + pooler_cpu_limit: Optional[str] = None, + pooler_memory_request: Optional[str] = None, + pooler_memory_limit: Optional[str] = None, + ) -> DedicatedDatabasePooler: + """ + Update the connection pooler configuration for a dedicated database. Configure pool mode, max connections, and pool sizes. + + Parameters + ---------- + database_id : str + Database ID. + mode : Optional[str] + Connection pool mode. Allowed values: transaction, session. Transaction mode returns connections to the pool after each transaction; session mode holds connections for the entire session lifetime. + max_connections : Optional[float] + Client-connection ceiling the pooler accepts. Supported on MySQL and MariaDB only; the PostgreSQL pooler has no client cap, so set networkMaxConnections on the database instead. + default_pool_size : Optional[float] + Default pool size per user. + read_write_splitting : Optional[bool] + Route SELECTs to HA replicas, writes and locked reads to the primary. Defaults to true when HA is enabled. + pooler_cpu_request : Optional[str] + Pooler sidecar CPU request override (Kubernetes quantity, e.g. "250m" or "1"). Leave null for the proportional default (5% of DB CPU, floor 100m). + pooler_cpu_limit : Optional[str] + Pooler sidecar CPU limit override (Kubernetes quantity, e.g. "500m" or "1"). Leave null for the proportional default (10% of DB CPU, floor 200m). Changing this field rolls the database pod. + pooler_memory_request : Optional[str] + Pooler sidecar memory request override (Kubernetes quantity, e.g. "128Mi" or "1Gi"). Leave null for the proportional default (7.5% of DB memory, floor 64Mi). + pooler_memory_limit : Optional[str] + Pooler sidecar memory limit override (Kubernetes quantity, e.g. "256Mi" or "1Gi"). Leave null for the proportional default (15% of DB memory, floor 128Mi). Changing this field rolls the database pod. + Returns + ------- + DedicatedDatabasePooler + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/pooler' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if mode is not None: + api_params['mode'] = self._normalize_value(mode) + if max_connections is not None: + api_params['maxConnections'] = self._normalize_value(max_connections) + if default_pool_size is not None: + api_params['defaultPoolSize'] = self._normalize_value(default_pool_size) + if read_write_splitting is not None: + api_params['readWriteSplitting'] = self._normalize_value(read_write_splitting) + if pooler_cpu_request is not None: + api_params['poolerCpuRequest'] = self._normalize_value(pooler_cpu_request) + if pooler_cpu_limit is not None: + api_params['poolerCpuLimit'] = self._normalize_value(pooler_cpu_limit) + if pooler_memory_request is not None: + api_params['poolerMemoryRequest'] = self._normalize_value(pooler_memory_request) + if pooler_memory_limit is not None: + api_params['poolerMemoryLimit'] = self._normalize_value(pooler_memory_limit) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabasePooler) + + def get_replicas( + self, + database_id: str, + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + def list_restorations( + self, + database_id: str, + status: Optional[str] = None, + type: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseRestorationList: + """ + List all restorations for a dedicated database. Results can be filtered by status and type. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by restoration status. + type : Optional[str] + Filter by restoration type. + limit : Optional[float] + Maximum number of restorations to return. + offset : Optional[float] + Number of restorations to skip. + Returns + ------- + DedicatedDatabaseRestorationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if type is not None: + api_params['type'] = self._normalize_value(type) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestorationList) + + def create_restoration( + self, + database_id: str, + type: Optional[str] = None, + backup_id: Optional[str] = None, + target_database_id: Optional[str] = None, + target_time: Optional[str] = None, + ) -> DedicatedDatabaseRestoration: + """ + Restore a database from a backup or to a specific point in time (PITR). For backup restoration, provide a backupId. For PITR, provide a targetTime as an ISO 8601 datetime. PITR requires the database to have PITR enabled and is only available for enterprise databases. + + Parameters + ---------- + database_id : str + Database ID. + type : Optional[str] + Restoration type. Allowed values: backup, pitr. Use "backup" to restore from a specific backup, or "pitr" for point-in-time recovery. + backup_id : Optional[str] + Backup ID to restore from (required for backup type). + target_database_id : Optional[str] + Existing database ID to restore into. The target must be distinct, ready, and use the same engine and version. + target_time : Optional[str] + Target time for PITR (required for pitr type) as an [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) datetime. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/restorations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if type is not None: + api_params['type'] = self._normalize_value(type) + if backup_id is not None: + api_params['backupId'] = self._normalize_value(backup_id) + if target_database_id is not None: + api_params['targetDatabaseId'] = self._normalize_value(target_database_id) + if target_time is not None: + api_params['targetTime'] = self._normalize_value(target_time) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_restoration( + self, + database_id: str, + restoration_id: str, + ) -> DedicatedDatabaseRestoration: + """ + Get details of a specific database restoration including its status, type, and timestamps. + + Parameters + ---------- + database_id : str + Database ID. + restoration_id : str + Restoration ID. + Returns + ------- + DedicatedDatabaseRestoration + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/restorations/{restorationId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if restoration_id is None: + raise AppwriteException('Missing required parameter: "restoration_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{restorationId}', str(self._normalize_value(restoration_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseRestoration) + + def get_status( + self, + database_id: str, + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseStatus) + + def create_upgrade( + self, + database_id: str, + target_version: str, + ) -> DedicatedDatabase: + """ + Upgrade a dedicated database to a new engine version. Uses blue-green deployment for zero-downtime cutover. + + Parameters + ---------- + database_id : str + Database ID. + target_version : str + Target engine version to upgrade to. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/postgresql/{databaseId}/upgrades' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if target_version is None: + raise AppwriteException('Missing required parameter: "target_version"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['targetVersion'] = self._normalize_value(target_version) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) diff --git a/appwrite/services/presences.py b/appwrite/services/presences.py index af9fd815..d4caaa86 100644 --- a/appwrite/services/presences.py +++ b/appwrite/services/presences.py @@ -6,6 +6,7 @@ from ..models.presence_list import PresenceList from ..models.presence import Presence + class Presences(Service): def __init__(self, client) -> None: @@ -15,11 +16,10 @@ def list( self, queries: Optional[List[str]] = None, total: Optional[bool] = None, - ttl: Optional[float] = None + ttl: Optional[float] = None, ) -> PresenceList: """ List presence logs. Expired entries are filtered out automatically. - Parameters ---------- @@ -29,12 +29,11 @@ def list( When set to false, the total count returned will be 0 and will not be calculated. ttl : Optional[float] TTL (seconds) for caching list responses. Responses are stored in an in-memory key-value cache, keyed per project, collection, schema version (attributes and indexes), caller authorization roles, and the exact query — so users with different permissions never share cached entries. Schema changes invalidate cached entries automatically; document writes do not, so choose a TTL you are comfortable serving as stale data. Set to 0 to disable caching. Must be between 0 and 86400 (24 hours). - Returns ------- PresenceList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -43,7 +42,6 @@ def list( api_path = '/presences' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: @@ -51,32 +49,34 @@ def list( if ttl is not None: api_params['ttl'] = self._normalize_value(ttl) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PresenceList) - def get( self, - presence_id: str + presence_id: str, ) -> Presence: """ Get a presence log by its unique ID. Entries whose `expiresAt` is in the past are treated as not found. - Parameters ---------- presence_id : str Presence unique ID. - Returns ------- Presence API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -87,18 +87,20 @@ def get( api_params = {} if presence_id is None: raise AppwriteException('Missing required parameter: "presence_id"') - api_path = api_path.replace('{presenceId}', str(self._normalize_value(presence_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Presence) - def upsert( self, presence_id: str, @@ -106,11 +108,10 @@ def upsert( status: str, permissions: Optional[List[str]] = None, expires_at: Optional[str] = None, - metadata: Optional[Dict[str, Any]] = None + metadata: Optional[Dict[str, Any]] = None, ) -> Presence: """ Create or update a presence log by its user ID. - Parameters ---------- @@ -126,12 +127,11 @@ def upsert( Presence expiry datetime. metadata : Optional[Dict[str, Any]] Presence metadata object. - Returns ------- Presence API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -142,15 +142,11 @@ def upsert( api_params = {} if presence_id is None: raise AppwriteException('Missing required parameter: "presence_id"') - if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if status is None: raise AppwriteException('Missing required parameter: "status"') - api_path = api_path.replace('{presenceId}', str(self._normalize_value(presence_id))) - api_params['userId'] = self._normalize_value(user_id) api_params['status'] = self._normalize_value(status) if permissions is not None: @@ -160,15 +156,19 @@ def upsert( if metadata is not None: api_params['metadata'] = self._normalize_value(metadata) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Presence) - def update( self, presence_id: str, @@ -177,11 +177,10 @@ def update( expires_at: Optional[str] = None, metadata: Optional[Dict[str, Any]] = None, permissions: Optional[List[str]] = None, - purge: Optional[bool] = None + purge: Optional[bool] = None, ) -> Presence: """ Update a presence log by its unique ID. Using the patch method you can pass only specific fields that will get updated. - Parameters ---------- @@ -199,12 +198,11 @@ def update( An array of permissions strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). purge : Optional[bool] When true, purge cached responses used by list presences endpoint. - Returns ------- Presence API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -215,12 +213,9 @@ def update( api_params = {} if presence_id is None: raise AppwriteException('Missing required parameter: "presence_id"') - if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{presenceId}', str(self._normalize_value(presence_id))) - api_params['userId'] = self._normalize_value(user_id) if status is not None: api_params['status'] = self._normalize_value(status) @@ -233,33 +228,35 @@ def update( if purge is not None: api_params['purge'] = self._normalize_value(purge) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Presence) - def delete( self, - presence_id: str + presence_id: str, ) -> Dict[str, Any]: """ Delete a presence log by its unique ID. - Parameters ---------- presence_id : str Presence unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -270,14 +267,16 @@ def delete( api_params = {} if presence_id is None: raise AppwriteException('Missing required parameter: "presence_id"') - api_path = api_path.replace('{presenceId}', str(self._normalize_value(presence_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/project.py b/appwrite/services/project.py index 1665fa81..be5c035e 100644 --- a/appwrite/services/project.py +++ b/appwrite/services/project.py @@ -33,6 +33,7 @@ from ..models.o_auth2_gitlab import OAuth2Gitlab from ..enums.project_o_auth2_google_prompt import ProjectOAuth2GooglePrompt from ..models.o_auth2_google import OAuth2Google +from ..models.o_auth2_hugging_face import OAuth2HuggingFace from ..models.o_auth2_keycloak import OAuth2Keycloak from ..models.o_auth2_kick import OAuth2Kick from ..models.o_auth2_linkedin import OAuth2Linkedin @@ -89,22 +90,22 @@ from ..models.variable_list import VariableList from ..models.variable import Variable + class Project(Service): def __init__(self, client) -> None: super(Project, self).__init__(client) def get( - self + self, ) -> ProjectModel: """ Get a project. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -114,24 +115,27 @@ def get( api_path = '/project' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def delete( - self + self, ) -> Dict[str, Any]: """ Delete a project. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -141,21 +145,25 @@ def delete( api_path = '/project' api_params = {} - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_auth_method( self, method_id: ProjectAuthMethodId, - enabled: bool + enabled: bool, ) -> ProjectModel: """ - Update properties of a specific auth method. Use this endpoint to enable or disable a method in your project. + Update properties of a specific auth method. Use this endpoint to enable or disable a method in your project. Parameters ---------- @@ -163,12 +171,11 @@ def update_auth_method( Auth Method ID. Possible values: email-password,magic-url,email-otp,anonymous,invites,jwt,phone enabled : bool Auth method status. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -179,27 +186,28 @@ def update_auth_method( api_params = {} if method_id is None: raise AppwriteException('Missing required parameter: "method_id"') - if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - api_path = api_path.replace('{methodId}', str(self._normalize_value(method_id))) - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def list_keys( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> KeyList: """ Get a list of all API keys from the current project. @@ -210,12 +218,11 @@ def list_keys( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: expire, accessedAt, name, scopes total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- KeyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -224,28 +231,31 @@ def list_keys( api_path = '/project/keys' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=KeyList) - def create_ephemeral_key( self, scopes: List[ProjectKeyScopes], - duration: float + duration: float, ) -> EphemeralKey: """ Create a new ephemeral API key. It's recommended to have multiple API keys with strict scopes for separate functions within your project. - + You can also create a standard API key if you need a longer-lived key instead. Parameters @@ -254,12 +264,11 @@ def create_ephemeral_key( Key scopes list. Maximum of 200 scopes are allowed. duration : float Time in seconds before ephemeral key expires. Maximum duration is 3600 seconds. - Returns ------- EphemeralKey API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -270,40 +279,40 @@ def create_ephemeral_key( api_params = {} if scopes is None: raise AppwriteException('Missing required parameter: "scopes"') - if duration is None: raise AppwriteException('Missing required parameter: "duration"') - - api_params['scopes'] = self._normalize_value(scopes) api_params['duration'] = self._normalize_value(duration) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=EphemeralKey) - def get_key( self, - key_id: str + key_id: str, ) -> Key: """ - Get a key by its unique ID. + Get a key by its unique ID. Parameters ---------- key_id : str Key ID. - Returns ------- Key API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -314,24 +323,26 @@ def get_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Key) - def update_key( self, key_id: str, name: str, scopes: List[ProjectKeyScopes], - expire: Optional[str] = None + expire: Optional[str] = None, ) -> Key: """ Update a key by its unique ID. Use this endpoint to update the name, scopes, or expiration time of an API key. @@ -346,12 +357,11 @@ def update_key( Key scopes list. Maximum of 200 scopes are allowed. expire : Optional[str] Expiration time in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Use null for unlimited expiration. - Returns ------- Key API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -362,32 +372,32 @@ def update_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if scopes is None: raise AppwriteException('Missing required parameter: "scopes"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - api_params['name'] = self._normalize_value(name) api_params['scopes'] = self._normalize_value(scopes) if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Key) - def delete_key( self, - key_id: str + key_id: str, ) -> Dict[str, Any]: """ Delete a key by its unique ID. Once deleted, the key can no longer be used to authenticate API calls. @@ -396,12 +406,11 @@ def delete_key( ---------- key_id : str Key ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -412,21 +421,23 @@ def delete_key( api_params = {} if key_id is None: raise AppwriteException('Missing required parameter: "key_id"') - api_path = api_path.replace('{keyId}', str(self._normalize_value(key_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_labels( self, - labels: List[str] + labels: List[str], ) -> ProjectModel: """ Update the project labels. Labels can be used to easily filter projects in an organization. @@ -435,12 +446,11 @@ def update_labels( ---------- labels : List[str] Array of project labels. Replaces the previous labels. Maximum of 1000 labels are allowed, each up to 36 alphanumeric characters long. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -451,23 +461,25 @@ def update_labels( api_params = {} if labels is None: raise AppwriteException('Missing required parameter: "labels"') - - api_params['labels'] = self._normalize_value(labels) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def list_mock_phones( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> MockNumberList: """ Get a list of all mock phones in the project. This endpoint returns an array of all mock phones and their OTPs. @@ -478,12 +490,11 @@ def list_mock_phones( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- MockNumberList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -492,24 +503,27 @@ def list_mock_phones( api_path = '/project/mock-phones' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MockNumberList) - def create_mock_phone( self, number: str, - otp: str + otp: str, ) -> MockNumber: """ Create a new mock phone for your project. Use this endpoint to register a mock phone number and its sign-in OTP for your testers. @@ -520,12 +534,11 @@ def create_mock_phone( Phone number to associate with the mock phone. Must be a valid E.164 formatted phone number. otp : str One-time password (OTP) to associate with the mock phone. Must be a 6-digit numeric code. - Returns ------- MockNumber API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -536,26 +549,27 @@ def create_mock_phone( api_params = {} if number is None: raise AppwriteException('Missing required parameter: "number"') - if otp is None: raise AppwriteException('Missing required parameter: "otp"') - - api_params['number'] = self._normalize_value(number) api_params['otp'] = self._normalize_value(otp) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MockNumber) - def get_mock_phone( self, - number: str + number: str, ) -> MockNumber: """ Get a mock phone by its unique number. This endpoint returns the mock phone's OTP. @@ -564,12 +578,11 @@ def get_mock_phone( ---------- number : str Phone number associated with the mock phone. Must be a valid E.164 formatted phone number. - Returns ------- MockNumber API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -580,22 +593,24 @@ def get_mock_phone( api_params = {} if number is None: raise AppwriteException('Missing required parameter: "number"') - api_path = api_path.replace('{number}', str(self._normalize_value(number))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MockNumber) - def update_mock_phone( self, number: str, - otp: str + otp: str, ) -> MockNumber: """ Update a mock phone by its unique number. Use this endpoint to update the mock phone's OTP. @@ -606,12 +621,11 @@ def update_mock_phone( Phone number associated with the mock phone. Must be a valid E.164 formatted phone number. otp : str One-time password (OTP) to associate with the mock phone. Must be a 6-digit numeric code. - Returns ------- MockNumber API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -622,26 +636,27 @@ def update_mock_phone( api_params = {} if number is None: raise AppwriteException('Missing required parameter: "number"') - if otp is None: raise AppwriteException('Missing required parameter: "otp"') - api_path = api_path.replace('{number}', str(self._normalize_value(number))) - api_params['otp'] = self._normalize_value(otp) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MockNumber) - def delete_mock_phone( self, - number: str + number: str, ) -> Dict[str, Any]: """ Delete a mock phone by its unique number. This endpoint removes the mock phone and its OTP configuration from the project. @@ -650,12 +665,11 @@ def delete_mock_phone( ---------- number : str Phone number associated with the mock phone. Must be a valid E.164 formatted phone number. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -666,22 +680,24 @@ def delete_mock_phone( api_params = {} if number is None: raise AppwriteException('Missing required parameter: "number"') - api_path = api_path.replace('{number}', str(self._normalize_value(number))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_o_auth2_providers( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> OAuth2ProviderList: """ Get a list of all OAuth2 providers supported by the server, along with the project's configuration for each. Credential fields are write-only and always returned empty. @@ -692,12 +708,11 @@ def list_o_auth2_providers( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- OAuth2ProviderList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -706,20 +721,23 @@ def list_o_auth2_providers( api_path = '/project/oauth2' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2ProviderList) - def update_o_auth2_server( self, enabled: bool, @@ -737,7 +755,7 @@ def update_o_auth2_server( user_code_format: Optional[str] = None, device_code_duration: Optional[float] = None, default_scopes: Optional[List[str]] = None, - installation_scopes: Optional[List[str]] = None + installation_scopes: Optional[List[str]] = None, ) -> ProjectModel: """ Update the OAuth2 server (OIDC provider) configuration. @@ -776,12 +794,11 @@ def update_o_auth2_server( List of OAuth2 scopes used when an authorization request omits the scope parameter. Every default scope must also be allowed by the OAuth2 server. Maximum of 100 scopes are allowed, each up to 128 characters long. installation_scopes : Optional[List[str]] List of scopes an application may request when installed on a team. Omitting the parameter clears the list, so no installation scopes can be granted. Maximum of 100 scopes are allowed, each up to 128 characters long. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -792,11 +809,8 @@ def update_o_auth2_server( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - if authorization_url is None: raise AppwriteException('Missing required parameter: "authorization_url"') - - api_params['enabled'] = self._normalize_value(enabled) api_params['authorizationUrl'] = self._normalize_value(authorization_url) if scopes is not None: @@ -828,20 +842,24 @@ def update_o_auth2_server( if installation_scopes is not None: api_params['installationScopes'] = self._normalize_value(installation_scopes) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_o_auth2_amazon( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Amazon: """ Update the project OAuth2 Amazon configuration. @@ -854,12 +872,11 @@ def update_o_auth2_amazon( 'Client Secret' of Amazon OAuth2 app. For example: 79ffe4000000000000000000000000000000000000000000000000000002de55 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Amazon API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -868,7 +885,6 @@ def update_o_auth2_amazon( api_path = '/project/oauth2/amazon' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -876,22 +892,26 @@ def update_o_auth2_amazon( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Amazon) - def update_o_auth2_apple( self, service_id: Optional[str] = None, key_id: Optional[str] = None, team_id: Optional[str] = None, p8_file: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Apple: """ Update the project OAuth2 Apple configuration. @@ -908,12 +928,11 @@ def update_o_auth2_apple( Contents of the Apple OAuth2 app .p8 private key file. The secret key wrapped by the PEM markers is 200 characters long. For example: -----BEGIN PRIVATE KEY-----MIGTAg...jy2Xbna-----END PRIVATE KEY----- enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Apple API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -922,7 +941,6 @@ def update_o_auth2_apple( api_path = '/project/oauth2/apple' api_params = {} - if service_id is not None: api_params['serviceId'] = self._normalize_value(service_id) if key_id is not None: @@ -934,20 +952,24 @@ def update_o_auth2_apple( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Apple) - def update_o_auth2_appwrite( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Appwrite: """ Update the project OAuth2 Appwrite configuration. @@ -960,12 +982,11 @@ def update_o_auth2_appwrite( 'Client Secret' of Appwrite OAuth2 app. For example: b86afd000000000000000000000000000000000000000000000000000ced5f93 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Appwrite API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -974,7 +995,6 @@ def update_o_auth2_appwrite( api_path = '/project/oauth2/appwrite' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -982,21 +1002,25 @@ def update_o_auth2_appwrite( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Appwrite) - def update_o_auth2_auth0( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, endpoint: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Auth0: """ Update the project OAuth2 Auth0 configuration. @@ -1011,12 +1035,11 @@ def update_o_auth2_auth0( Domain of Auth0 instance. For example: example.us.auth0.com enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Auth0 API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1025,7 +1048,6 @@ def update_o_auth2_auth0( api_path = '/project/oauth2/auth0' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1035,21 +1057,25 @@ def update_o_auth2_auth0( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Auth0) - def update_o_auth2_authentik( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, endpoint: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Authentik: """ Update the project OAuth2 Authentik configuration. @@ -1064,12 +1090,11 @@ def update_o_auth2_authentik( Domain of Authentik instance. For example: example.authentik.com enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Authentik API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1078,7 +1103,6 @@ def update_o_auth2_authentik( api_path = '/project/oauth2/authentik' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1088,20 +1112,24 @@ def update_o_auth2_authentik( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Authentik) - def update_o_auth2_autodesk( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Autodesk: """ Update the project OAuth2 Autodesk configuration. @@ -1114,12 +1142,11 @@ def update_o_auth2_autodesk( 'Client Secret' of Autodesk OAuth2 app. For example: 7I000000000000MW enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Autodesk API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1128,7 +1155,6 @@ def update_o_auth2_autodesk( api_path = '/project/oauth2/autodesk' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1136,20 +1162,24 @@ def update_o_auth2_autodesk( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Autodesk) - def update_o_auth2_bitbucket( self, key: Optional[str] = None, secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Bitbucket: """ Update the project OAuth2 Bitbucket configuration. @@ -1162,12 +1192,11 @@ def update_o_auth2_bitbucket( 'Secret' of Bitbucket OAuth2 app. For example: NMfLZJ00000000000000000000TLQdDx enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Bitbucket API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1176,7 +1205,6 @@ def update_o_auth2_bitbucket( api_path = '/project/oauth2/bitbucket' api_params = {} - if key is not None: api_params['key'] = self._normalize_value(key) if secret is not None: @@ -1184,20 +1212,24 @@ def update_o_auth2_bitbucket( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Bitbucket) - def update_o_auth2_bitly( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Bitly: """ Update the project OAuth2 Bitly configuration. @@ -1210,12 +1242,11 @@ def update_o_auth2_bitly( 'Client Secret' of Bitly OAuth2 app. For example: a13e250000000000000000000000000000d73095 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Bitly API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1224,7 +1255,6 @@ def update_o_auth2_bitly( api_path = '/project/oauth2/bitly' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1232,20 +1262,24 @@ def update_o_auth2_bitly( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Bitly) - def update_o_auth2_box( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Box: """ Update the project OAuth2 Box configuration. @@ -1258,12 +1292,11 @@ def update_o_auth2_box( 'Client Secret' of Box OAuth2 app. For example: OKM1f100000000000000000000eshEif enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Box API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1272,7 +1305,6 @@ def update_o_auth2_box( api_path = '/project/oauth2/box' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1280,20 +1312,24 @@ def update_o_auth2_box( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Box) - def update_o_auth2_dailymotion( self, api_key: Optional[str] = None, api_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Dailymotion: """ Update the project OAuth2 Dailymotion configuration. @@ -1306,12 +1342,11 @@ def update_o_auth2_dailymotion( 'API Secret' of Dailymotion OAuth2 app. For example: a399a90000000000000000000000000000d90639 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Dailymotion API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1320,7 +1355,6 @@ def update_o_auth2_dailymotion( api_path = '/project/oauth2/dailymotion' api_params = {} - if api_key is not None: api_params['apiKey'] = self._normalize_value(api_key) if api_secret is not None: @@ -1328,20 +1362,24 @@ def update_o_auth2_dailymotion( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Dailymotion) - def update_o_auth2_discord( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Discord: """ Update the project OAuth2 Discord configuration. @@ -1354,12 +1392,11 @@ def update_o_auth2_discord( 'Client Secret' of Discord OAuth2 app. For example: YmPXnM000000000000000000002zFg5D enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Discord API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1368,7 +1405,6 @@ def update_o_auth2_discord( api_path = '/project/oauth2/discord' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1376,20 +1412,24 @@ def update_o_auth2_discord( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Discord) - def update_o_auth2_disqus( self, public_key: Optional[str] = None, secret_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Disqus: """ Update the project OAuth2 Disqus configuration. @@ -1402,12 +1442,11 @@ def update_o_auth2_disqus( 'Secret Key, also known as API Secret' of Disqus OAuth2 app. For example: W7Bykj00000000000000000000000000000000000000000000000000003o43w9 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Disqus API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1416,7 +1455,6 @@ def update_o_auth2_disqus( api_path = '/project/oauth2/disqus' api_params = {} - if public_key is not None: api_params['publicKey'] = self._normalize_value(public_key) if secret_key is not None: @@ -1424,20 +1462,24 @@ def update_o_auth2_disqus( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Disqus) - def update_o_auth2_dropbox( self, app_key: Optional[str] = None, app_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Dropbox: """ Update the project OAuth2 Dropbox configuration. @@ -1450,12 +1492,11 @@ def update_o_auth2_dropbox( 'App Secret' of Dropbox OAuth2 app. For example: g200000000000vw enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Dropbox API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1464,7 +1505,6 @@ def update_o_auth2_dropbox( api_path = '/project/oauth2/dropbox' api_params = {} - if app_key is not None: api_params['appKey'] = self._normalize_value(app_key) if app_secret is not None: @@ -1472,20 +1512,24 @@ def update_o_auth2_dropbox( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Dropbox) - def update_o_auth2_etsy( self, key_string: Optional[str] = None, shared_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Etsy: """ Update the project OAuth2 Etsy configuration. @@ -1498,12 +1542,11 @@ def update_o_auth2_etsy( 'Shared Secret' of Etsy OAuth2 app. For example: tp000000ru enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Etsy API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1512,7 +1555,6 @@ def update_o_auth2_etsy( api_path = '/project/oauth2/etsy' api_params = {} - if key_string is not None: api_params['keyString'] = self._normalize_value(key_string) if shared_secret is not None: @@ -1520,20 +1562,24 @@ def update_o_auth2_etsy( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Etsy) - def update_o_auth2_facebook( self, app_id: Optional[str] = None, app_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Facebook: """ Update the project OAuth2 Facebook configuration. @@ -1546,12 +1592,11 @@ def update_o_auth2_facebook( 'App Secret' of Facebook OAuth2 app. For example: 2d0b2800000000000000000000d38af4 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Facebook API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1560,7 +1605,6 @@ def update_o_auth2_facebook( api_path = '/project/oauth2/facebook' api_params = {} - if app_id is not None: api_params['appId'] = self._normalize_value(app_id) if app_secret is not None: @@ -1568,20 +1612,24 @@ def update_o_auth2_facebook( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Facebook) - def update_o_auth2_figma( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Figma: """ Update the project OAuth2 Figma configuration. @@ -1594,12 +1642,11 @@ def update_o_auth2_figma( 'Client Secret' of Figma OAuth2 app. For example: yEpOYn0000000000000000004iIsU5 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Figma API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1608,7 +1655,6 @@ def update_o_auth2_figma( api_path = '/project/oauth2/figma' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1616,21 +1662,25 @@ def update_o_auth2_figma( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Figma) - def update_o_auth2_fusion_auth( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, endpoint: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2FusionAuth: """ Update the project OAuth2 FusionAuth configuration. @@ -1645,12 +1695,11 @@ def update_o_auth2_fusion_auth( Domain of FusionAuth instance. For example: example.fusionauth.io enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2FusionAuth API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1659,7 +1708,6 @@ def update_o_auth2_fusion_auth( api_path = '/project/oauth2/fusionauth' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1669,20 +1717,24 @@ def update_o_auth2_fusion_auth( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2FusionAuth) - def update_o_auth2_git_hub( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Github: """ Update the project OAuth2 GitHub configuration. @@ -1695,12 +1747,11 @@ def update_o_auth2_git_hub( 'Client Secret' of GitHub OAuth2 app. For example: 5e07c00000000000000000000000000000198bcc enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Github API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1709,7 +1760,6 @@ def update_o_auth2_git_hub( api_path = '/project/oauth2/github' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1717,21 +1767,25 @@ def update_o_auth2_git_hub( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Github) - def update_o_auth2_gitlab( self, application_id: Optional[str] = None, secret: Optional[str] = None, endpoint: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Gitlab: """ Update the project OAuth2 Gitlab configuration. @@ -1746,12 +1800,11 @@ def update_o_auth2_gitlab( Endpoint URL of self-hosted GitLab instance. For example: https://gitlab.com enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Gitlab API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1760,7 +1813,6 @@ def update_o_auth2_gitlab( api_path = '/project/oauth2/gitlab' api_params = {} - if application_id is not None: api_params['applicationId'] = self._normalize_value(application_id) if secret is not None: @@ -1770,21 +1822,25 @@ def update_o_auth2_gitlab( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Gitlab) - def update_o_auth2_google( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, prompt: Optional[List[ProjectOAuth2GooglePrompt]] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Google: """ Update the project OAuth2 Google configuration. @@ -1799,12 +1855,11 @@ def update_o_auth2_google( Array of Google OAuth2 prompt values. If "none" is included, it must be the only element. "none" means: don't display any authentication or consent screens. Must not be specified with other values. "consent" means: prompt the user for consent. "select_account" means: prompt the user to select an account. enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Google API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1813,7 +1868,6 @@ def update_o_auth2_google( api_path = '/project/oauth2/google' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1823,14 +1877,68 @@ def update_o_auth2_google( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Google) + def update_o_auth2_hugging_face( + self, + client_id: Optional[str] = None, + client_secret: Optional[str] = None, + enabled: Optional[bool] = None, + ) -> OAuth2HuggingFace: + """ + Update the project OAuth2 Hugging Face configuration. + + Parameters + ---------- + client_id : Optional[str] + 'Client ID' of Hugging Face OAuth2 app. For example: 2ab9cff9-d711-40ad-a91e-b08a49c42d24 + client_secret : Optional[str] + 'Client Secret' of Hugging Face OAuth2 app. For example: oauth_app_secret_wcLhRtl000000000000000000000xbNdLt + enabled : Optional[bool] + OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. + Returns + ------- + OAuth2HuggingFace + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/project/oauth2/huggingface' + api_params = {} + if client_id is not None: + api_params['clientId'] = self._normalize_value(client_id) + if client_secret is not None: + api_params['clientSecret'] = self._normalize_value(client_secret) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=OAuth2HuggingFace) def update_o_auth2_keycloak( self, @@ -1838,7 +1946,7 @@ def update_o_auth2_keycloak( client_secret: Optional[str] = None, endpoint: Optional[str] = None, realm_name: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Keycloak: """ Update the project OAuth2 Keycloak configuration. @@ -1855,12 +1963,11 @@ def update_o_auth2_keycloak( Keycloak realm name. For example: appwrite-realm enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Keycloak API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1869,7 +1976,6 @@ def update_o_auth2_keycloak( api_path = '/project/oauth2/keycloak' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1881,20 +1987,24 @@ def update_o_auth2_keycloak( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Keycloak) - def update_o_auth2_kick( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Kick: """ Update the project OAuth2 Kick configuration. @@ -1907,12 +2017,11 @@ def update_o_auth2_kick( 'Client Secret' of Kick OAuth2 app. For example: 34ac5600000000000000000000000000000000000000000000000000e830c8b enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Kick API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1921,7 +2030,6 @@ def update_o_auth2_kick( api_path = '/project/oauth2/kick' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -1929,20 +2037,24 @@ def update_o_auth2_kick( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Kick) - def update_o_auth2_linkedin( self, client_id: Optional[str] = None, primary_client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Linkedin: """ Update the project OAuth2 Linkedin configuration. @@ -1955,12 +2067,11 @@ def update_o_auth2_linkedin( 'Primary Client Secret or Secondary Client Secret' of Linkedin OAuth2 app. For example: WPL_AP1.2Bf0000000000000./HtlYw== enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Linkedin API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1969,7 +2080,6 @@ def update_o_auth2_linkedin( api_path = '/project/oauth2/linkedin' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if primary_client_secret is not None: @@ -1977,21 +2087,25 @@ def update_o_auth2_linkedin( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Linkedin) - def update_o_auth2_microsoft( self, application_id: Optional[str] = None, application_secret: Optional[str] = None, tenant: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Microsoft: """ Update the project OAuth2 Microsoft configuration. @@ -2006,12 +2120,11 @@ def update_o_auth2_microsoft( Microsoft Entra ID tenant identifier. Use 'common', 'organizations', 'consumers' or a specific tenant ID. For example: common enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Microsoft API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2020,7 +2133,6 @@ def update_o_auth2_microsoft( api_path = '/project/oauth2/microsoft' api_params = {} - if application_id is not None: api_params['applicationId'] = self._normalize_value(application_id) if application_secret is not None: @@ -2030,20 +2142,24 @@ def update_o_auth2_microsoft( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Microsoft) - def update_o_auth2_notion( self, oauth_client_id: Optional[str] = None, oauth_client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Notion: """ Update the project OAuth2 Notion configuration. @@ -2056,12 +2172,11 @@ def update_o_auth2_notion( 'OAuth Client Secret' of Notion OAuth2 app. For example: secret_dLUr4b000000000000000000000000000000lFHAa9 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Notion API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2070,7 +2185,6 @@ def update_o_auth2_notion( api_path = '/project/oauth2/notion' api_params = {} - if oauth_client_id is not None: api_params['oauthClientId'] = self._normalize_value(oauth_client_id) if oauth_client_secret is not None: @@ -2078,15 +2192,19 @@ def update_o_auth2_notion( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Notion) - def update_o_auth2_oidc( self, client_id: Optional[str] = None, @@ -2097,7 +2215,7 @@ def update_o_auth2_oidc( user_info_url: Optional[str] = None, prompt: Optional[List[ProjectOAuth2OidcPrompt]] = None, max_age: Optional[float] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Oidc: """ Update the project OAuth2 Oidc configuration. @@ -2122,12 +2240,11 @@ def update_o_auth2_oidc( Maximum authentication age in seconds. When set, the user must have authenticated within this many seconds, otherwise they are prompted to re-authenticate. enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Oidc API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2136,7 +2253,6 @@ def update_o_auth2_oidc( api_path = '/project/oauth2/oidc' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2156,22 +2272,26 @@ def update_o_auth2_oidc( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Oidc) - def update_o_auth2_okta( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, domain: Optional[str] = None, authorization_server_id: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Okta: """ Update the project OAuth2 Okta configuration. @@ -2188,12 +2308,11 @@ def update_o_auth2_okta( Custom Authorization Servers. Optional, can be left empty or unconfigured. For example: aus000000000000000h7z enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Okta API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2202,7 +2321,6 @@ def update_o_auth2_okta( api_path = '/project/oauth2/okta' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2214,20 +2332,24 @@ def update_o_auth2_okta( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Okta) - def update_o_auth2_paypal( self, client_id: Optional[str] = None, secret_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Paypal: """ Update the project OAuth2 Paypal configuration. @@ -2240,12 +2362,11 @@ def update_o_auth2_paypal( 'Secret Key 1 or Secret Key 2' of Paypal OAuth2 app. For example: EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Paypal API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2254,7 +2375,6 @@ def update_o_auth2_paypal( api_path = '/project/oauth2/paypal' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if secret_key is not None: @@ -2262,20 +2382,24 @@ def update_o_auth2_paypal( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Paypal) - def update_o_auth2_paypal_sandbox( self, client_id: Optional[str] = None, secret_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Paypal: """ Update the project OAuth2 PaypalSandbox configuration. @@ -2288,12 +2412,11 @@ def update_o_auth2_paypal_sandbox( 'Secret Key 1 or Secret Key 2' of PaypalSandbox OAuth2 app. For example: EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Paypal API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2302,7 +2425,6 @@ def update_o_auth2_paypal_sandbox( api_path = '/project/oauth2/paypalSandbox' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if secret_key is not None: @@ -2310,20 +2432,24 @@ def update_o_auth2_paypal_sandbox( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Paypal) - def update_o_auth2_podio( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Podio: """ Update the project OAuth2 Podio configuration. @@ -2336,12 +2462,11 @@ def update_o_auth2_podio( 'Client Secret' of Podio OAuth2 app. For example: Rn247T0000000000000000000000000000000000000000000000000000W2zWTN enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Podio API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2350,7 +2475,6 @@ def update_o_auth2_podio( api_path = '/project/oauth2/podio' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2358,20 +2482,24 @@ def update_o_auth2_podio( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Podio) - def update_o_auth2_salesforce( self, customer_key: Optional[str] = None, customer_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Salesforce: """ Update the project OAuth2 Salesforce configuration. @@ -2384,12 +2512,11 @@ def update_o_auth2_salesforce( 'Consumer Secret' of Salesforce OAuth2 app. For example: 3w000000000000e2 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Salesforce API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2398,7 +2525,6 @@ def update_o_auth2_salesforce( api_path = '/project/oauth2/salesforce' api_params = {} - if customer_key is not None: api_params['customerKey'] = self._normalize_value(customer_key) if customer_secret is not None: @@ -2406,20 +2532,24 @@ def update_o_auth2_salesforce( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Salesforce) - def update_o_auth2_slack( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Slack: """ Update the project OAuth2 Slack configuration. @@ -2432,12 +2562,11 @@ def update_o_auth2_slack( 'Client Secret' of Slack OAuth2 app. For example: 81656000000000000000000000f3d2fd enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Slack API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2446,7 +2575,6 @@ def update_o_auth2_slack( api_path = '/project/oauth2/slack' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2454,20 +2582,24 @@ def update_o_auth2_slack( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Slack) - def update_o_auth2_spotify( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Spotify: """ Update the project OAuth2 Spotify configuration. @@ -2480,12 +2612,11 @@ def update_o_auth2_spotify( 'Client Secret' of Spotify OAuth2 app. For example: db068a000000000000000000008b5b9f enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Spotify API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2494,7 +2625,6 @@ def update_o_auth2_spotify( api_path = '/project/oauth2/spotify' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2502,20 +2632,24 @@ def update_o_auth2_spotify( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Spotify) - def update_o_auth2_stripe( self, client_id: Optional[str] = None, api_secret_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Stripe: """ Update the project OAuth2 Stripe configuration. @@ -2528,12 +2662,11 @@ def update_o_auth2_stripe( 'API Secret Key' of Stripe OAuth2 app. For example: sk_51SfOd000000000000000000000000000000000000000000000000000000000000000000000000000000000000000QGWYfp enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Stripe API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2542,7 +2675,6 @@ def update_o_auth2_stripe( api_path = '/project/oauth2/stripe' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if api_secret_key is not None: @@ -2550,20 +2682,24 @@ def update_o_auth2_stripe( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Stripe) - def update_o_auth2_tradeshift( self, oauth2_client_id: Optional[str] = None, oauth2_client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Tradeshift: """ Update the project OAuth2 Tradeshift configuration. @@ -2576,12 +2712,11 @@ def update_o_auth2_tradeshift( 'OAuth2 Client Secret' of Tradeshift OAuth2 app. For example: 7cb52700-0000-0000-0000-000000ca5b83 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Tradeshift API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2590,7 +2725,6 @@ def update_o_auth2_tradeshift( api_path = '/project/oauth2/tradeshift' api_params = {} - if oauth2_client_id is not None: api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) if oauth2_client_secret is not None: @@ -2598,20 +2732,24 @@ def update_o_auth2_tradeshift( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Tradeshift) - def update_o_auth2_tradeshift_sandbox( self, oauth2_client_id: Optional[str] = None, oauth2_client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Tradeshift: """ Update the project OAuth2 Tradeshift Sandbox configuration. @@ -2624,12 +2762,11 @@ def update_o_auth2_tradeshift_sandbox( 'OAuth2 Client Secret' of Tradeshift Sandbox OAuth2 app. For example: 7cb52700-0000-0000-0000-000000ca5b83 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Tradeshift API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2638,7 +2775,6 @@ def update_o_auth2_tradeshift_sandbox( api_path = '/project/oauth2/tradeshiftBox' api_params = {} - if oauth2_client_id is not None: api_params['oauth2ClientId'] = self._normalize_value(oauth2_client_id) if oauth2_client_secret is not None: @@ -2646,20 +2782,24 @@ def update_o_auth2_tradeshift_sandbox( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Tradeshift) - def update_o_auth2_twitch( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Twitch: """ Update the project OAuth2 Twitch configuration. @@ -2672,12 +2812,11 @@ def update_o_auth2_twitch( 'Client Secret' of Twitch OAuth2 app. For example: pmapue000000000000000000zylw3v enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Twitch API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2686,7 +2825,6 @@ def update_o_auth2_twitch( api_path = '/project/oauth2/twitch' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2694,20 +2832,24 @@ def update_o_auth2_twitch( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Twitch) - def update_o_auth2_word_press( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2WordPress: """ Update the project OAuth2 WordPress configuration. @@ -2720,12 +2862,11 @@ def update_o_auth2_word_press( 'Client Secret' of WordPress OAuth2 app. For example: PlBfJS0000000000000000000000000000000000000000000000000000EdUZJk enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2WordPress API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2734,7 +2875,6 @@ def update_o_auth2_word_press( api_path = '/project/oauth2/wordpress' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2742,20 +2882,24 @@ def update_o_auth2_word_press( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2WordPress) - def update_o_auth2_x( self, customer_key: Optional[str] = None, secret_key: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2X: """ Update the project OAuth2 X configuration. @@ -2768,12 +2912,11 @@ def update_o_auth2_x( 'Secret Key' of X OAuth2 app. For example: tkEPkp00000000000000000000000000000000000000FTxbI9 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2X API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2782,7 +2925,6 @@ def update_o_auth2_x( api_path = '/project/oauth2/x' api_params = {} - if customer_key is not None: api_params['customerKey'] = self._normalize_value(customer_key) if secret_key is not None: @@ -2790,20 +2932,24 @@ def update_o_auth2_x( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2X) - def update_o_auth2_yahoo( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Yahoo: """ Update the project OAuth2 Yahoo configuration. @@ -2816,12 +2962,11 @@ def update_o_auth2_yahoo( 'Client Secret, also known as Customer Secret' of Yahoo OAuth2 app. For example: cf978f0000000000000000000000000000c5e2e9 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Yahoo API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2830,7 +2975,6 @@ def update_o_auth2_yahoo( api_path = '/project/oauth2/yahoo' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2838,20 +2982,24 @@ def update_o_auth2_yahoo( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Yahoo) - def update_o_auth2_yandex( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Yandex: """ Update the project OAuth2 Yandex configuration. @@ -2864,12 +3012,11 @@ def update_o_auth2_yandex( 'Client Secret' of Yandex OAuth2 app. For example: bbf98500000000000000000000c75a63 enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Yandex API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2878,7 +3025,6 @@ def update_o_auth2_yandex( api_path = '/project/oauth2/yandex' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2886,20 +3032,24 @@ def update_o_auth2_yandex( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Yandex) - def update_o_auth2_zoho( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Zoho: """ Update the project OAuth2 Zoho configuration. @@ -2912,12 +3062,11 @@ def update_o_auth2_zoho( 'Client Secret' of Zoho OAuth2 app. For example: fb5cac000000000000000000000000000000a68f6e enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Zoho API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2926,7 +3075,6 @@ def update_o_auth2_zoho( api_path = '/project/oauth2/zoho' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2934,20 +3082,24 @@ def update_o_auth2_zoho( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Zoho) - def update_o_auth2_zoom( self, client_id: Optional[str] = None, client_secret: Optional[str] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> OAuth2Zoom: """ Update the project OAuth2 Zoom configuration. @@ -2960,12 +3112,11 @@ def update_o_auth2_zoom( 'Client Secret' of Zoom OAuth2 app. For example: GAWsG4000000000000000000007U01ON enabled : Optional[bool] OAuth2 sign-in method status. Set to true to enable new session creation. Setting to true will trigger end-to-end credentials validation, and will throw if the credentials are invalid. - Returns ------- OAuth2Zoom API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2974,7 +3125,6 @@ def update_o_auth2_zoom( api_path = '/project/oauth2/zoom' api_params = {} - if client_id is not None: api_params['clientId'] = self._normalize_value(client_id) if client_secret is not None: @@ -2982,19 +3132,65 @@ def update_o_auth2_zoom( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=OAuth2Zoom) - def get_o_auth2_provider( self, - provider_id: ProjectOAuthProviderId - ) -> Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft]: + provider_id: ProjectOAuthProviderId, + ) -> Union[ + OAuth2Github, + OAuth2Discord, + OAuth2Figma, + OAuth2Dropbox, + OAuth2Dailymotion, + OAuth2Bitbucket, + OAuth2Bitly, + OAuth2Box, + OAuth2Autodesk, + OAuth2Google, + OAuth2Zoom, + OAuth2Zoho, + OAuth2Yandex, + OAuth2X, + OAuth2WordPress, + OAuth2Twitch, + OAuth2Stripe, + OAuth2Spotify, + OAuth2Slack, + OAuth2Podio, + OAuth2Notion, + OAuth2Salesforce, + OAuth2Yahoo, + OAuth2HuggingFace, + OAuth2Linkedin, + OAuth2Disqus, + OAuth2Amazon, + OAuth2Etsy, + OAuth2Facebook, + OAuth2Tradeshift, + OAuth2Paypal, + OAuth2Gitlab, + OAuth2Authentik, + OAuth2Auth0, + OAuth2FusionAuth, + OAuth2Keycloak, + OAuth2Oidc, + OAuth2Apple, + OAuth2Okta, + OAuth2Kick, + OAuth2Microsoft, + ]: """ Get a single OAuth2 provider configuration. Credential fields (client secret, p8 file, key/team IDs) are write-only and always returned empty. @@ -3002,12 +3198,11 @@ def get_o_auth2_provider( ---------- provider_id : ProjectOAuthProviderId OAuth2 provider key. For example: github, google, apple. - Returns ------- - Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft] + Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2HuggingFace, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft] API response as one of the typed response models - + Raises ------ AppwriteException @@ -3018,14 +3213,17 @@ def get_o_auth2_provider( api_params = {} if provider_id is None: raise AppwriteException('Missing required parameter: "provider_id"') - api_path = api_path.replace('{providerId}', str(self._normalize_value(provider_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) if not isinstance(response, dict): raise AppwriteException('Expected object response when hydrating a response model') @@ -3098,6 +3296,9 @@ def get_o_auth2_provider( if response.get('$id') == 'yahoo': return self._parse_response(response, model=OAuth2Yahoo) + if response.get('$id') == 'huggingface': + return self._parse_response(response, model=OAuth2HuggingFace) + if response.get('$id') == 'linkedin': return self._parse_response(response, model=OAuth2Linkedin) @@ -3151,11 +3352,10 @@ def get_o_auth2_provider( raise AppwriteException('Unable to match response to any known model') - def list_platforms( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> PlatformList: """ Get a list of all platforms in the project. This endpoint returns an array of all platforms and their configurations. @@ -3166,12 +3366,11 @@ def list_platforms( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: type, name, hostname, bundleIdentifier, applicationId, packageIdentifierName, packageName total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- PlatformList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3180,25 +3379,28 @@ def list_platforms( api_path = '/project/platforms' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformList) - def create_android_platform( self, platform_id: str, name: str, - application_id: str + application_id: str, ) -> PlatformAndroid: """ Create a new Android platform for your project. Use this endpoint to register a new Android platform where your users will run your application which will interact with the Appwrite API. @@ -3211,12 +3413,11 @@ def create_android_platform( Platform name. Max length: 128 chars. application_id : str Android application ID. Max length: 256 chars. - Returns ------- PlatformAndroid API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3227,32 +3428,32 @@ def create_android_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if application_id is None: raise AppwriteException('Missing required parameter: "application_id"') - - api_params['platformId'] = self._normalize_value(platform_id) api_params['name'] = self._normalize_value(name) api_params['applicationId'] = self._normalize_value(application_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformAndroid) - def update_android_platform( self, platform_id: str, name: str, - application_id: str + application_id: str, ) -> PlatformAndroid: """ Update an Android platform by its unique ID. Use this endpoint to update the platform's name or application ID. @@ -3265,12 +3466,11 @@ def update_android_platform( Platform name. Max length: 128 chars. application_id : str Android application ID. Max length: 256 chars. - Returns ------- PlatformAndroid API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3281,32 +3481,32 @@ def update_android_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if application_id is None: raise AppwriteException('Missing required parameter: "application_id"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - api_params['name'] = self._normalize_value(name) api_params['applicationId'] = self._normalize_value(application_id) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformAndroid) - def create_apple_platform( self, platform_id: str, name: str, - bundle_identifier: str + bundle_identifier: str, ) -> PlatformApple: """ Create a new Apple platform for your project. Use this endpoint to register a new Apple platform where your users will run your application which will interact with the Appwrite API. @@ -3319,12 +3519,11 @@ def create_apple_platform( Platform name. Max length: 128 chars. bundle_identifier : str Apple bundle identifier. Max length: 256 chars. - Returns ------- PlatformApple API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3335,32 +3534,32 @@ def create_apple_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if bundle_identifier is None: raise AppwriteException('Missing required parameter: "bundle_identifier"') - - api_params['platformId'] = self._normalize_value(platform_id) api_params['name'] = self._normalize_value(name) api_params['bundleIdentifier'] = self._normalize_value(bundle_identifier) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformApple) - def update_apple_platform( self, platform_id: str, name: str, - bundle_identifier: str + bundle_identifier: str, ) -> PlatformApple: """ Update an Apple platform by its unique ID. Use this endpoint to update the platform's name or bundle identifier. @@ -3373,12 +3572,11 @@ def update_apple_platform( Platform name. Max length: 128 chars. bundle_identifier : str Apple bundle identifier. Max length: 256 chars. - Returns ------- PlatformApple API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3389,32 +3587,32 @@ def update_apple_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if bundle_identifier is None: raise AppwriteException('Missing required parameter: "bundle_identifier"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - api_params['name'] = self._normalize_value(name) api_params['bundleIdentifier'] = self._normalize_value(bundle_identifier) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformApple) - def create_linux_platform( self, platform_id: str, name: str, - package_name: str + package_name: str, ) -> PlatformLinux: """ Create a new Linux platform for your project. Use this endpoint to register a new Linux platform where your users will run your application which will interact with the Appwrite API. @@ -3427,12 +3625,11 @@ def create_linux_platform( Platform name. Max length: 128 chars. package_name : str Linux package name. Max length: 256 chars. - Returns ------- PlatformLinux API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3443,32 +3640,32 @@ def create_linux_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if package_name is None: raise AppwriteException('Missing required parameter: "package_name"') - - api_params['platformId'] = self._normalize_value(platform_id) api_params['name'] = self._normalize_value(name) api_params['packageName'] = self._normalize_value(package_name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformLinux) - def update_linux_platform( self, platform_id: str, name: str, - package_name: str + package_name: str, ) -> PlatformLinux: """ Update a Linux platform by its unique ID. Use this endpoint to update the platform's name or package name. @@ -3481,12 +3678,11 @@ def update_linux_platform( Platform name. Max length: 128 chars. package_name : str Linux package name. Max length: 256 chars. - Returns ------- PlatformLinux API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3497,32 +3693,32 @@ def update_linux_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if package_name is None: raise AppwriteException('Missing required parameter: "package_name"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - api_params['name'] = self._normalize_value(name) api_params['packageName'] = self._normalize_value(package_name) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformLinux) - def create_web_platform( self, platform_id: str, name: str, - hostname: str + hostname: str, ) -> PlatformWeb: """ Create a new web platform for your project. Use this endpoint to register a new platform where your users will run your application which will interact with the Appwrite API. @@ -3535,12 +3731,11 @@ def create_web_platform( Platform name. Max length: 128 chars. hostname : str Platform web hostname. Max length: 256 chars. - Returns ------- PlatformWeb API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3551,32 +3746,32 @@ def create_web_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if hostname is None: raise AppwriteException('Missing required parameter: "hostname"') - - api_params['platformId'] = self._normalize_value(platform_id) api_params['name'] = self._normalize_value(name) api_params['hostname'] = self._normalize_value(hostname) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformWeb) - def update_web_platform( self, platform_id: str, name: str, - hostname: str + hostname: str, ) -> PlatformWeb: """ Update a web platform by its unique ID. Use this endpoint to update the platform's name or hostname. @@ -3589,12 +3784,11 @@ def update_web_platform( Platform name. Max length: 128 chars. hostname : str Platform web hostname. Max length: 256 chars. - Returns ------- PlatformWeb API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3605,32 +3799,32 @@ def update_web_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if hostname is None: raise AppwriteException('Missing required parameter: "hostname"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - api_params['name'] = self._normalize_value(name) api_params['hostname'] = self._normalize_value(hostname) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformWeb) - def create_windows_platform( self, platform_id: str, name: str, - package_identifier_name: str + package_identifier_name: str, ) -> PlatformWindows: """ Create a new Windows platform for your project. Use this endpoint to register a new Windows platform where your users will run your application which will interact with the Appwrite API. @@ -3643,12 +3837,11 @@ def create_windows_platform( Platform name. Max length: 128 chars. package_identifier_name : str Windows package identifier name. Max length: 256 chars. - Returns ------- PlatformWindows API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3659,32 +3852,32 @@ def create_windows_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if package_identifier_name is None: raise AppwriteException('Missing required parameter: "package_identifier_name"') - - api_params['platformId'] = self._normalize_value(platform_id) api_params['name'] = self._normalize_value(name) api_params['packageIdentifierName'] = self._normalize_value(package_identifier_name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformWindows) - def update_windows_platform( self, platform_id: str, name: str, - package_identifier_name: str + package_identifier_name: str, ) -> PlatformWindows: """ Update a Windows platform by its unique ID. Use this endpoint to update the platform's name or package identifier name. @@ -3697,12 +3890,11 @@ def update_windows_platform( Platform name. Max length: 128 chars. package_identifier_name : str Windows package identifier name. Max length: 256 chars. - Returns ------- PlatformWindows API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3713,31 +3905,37 @@ def update_windows_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if package_identifier_name is None: raise AppwriteException('Missing required parameter: "package_identifier_name"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - api_params['name'] = self._normalize_value(name) api_params['packageIdentifierName'] = self._normalize_value(package_identifier_name) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PlatformWindows) - def get_platform( self, - platform_id: str - ) -> Union[PlatformWeb, PlatformApple, PlatformAndroid, PlatformWindows, PlatformLinux]: + platform_id: str, + ) -> Union[ + PlatformWeb, + PlatformApple, + PlatformAndroid, + PlatformWindows, + PlatformLinux, + ]: """ Get a platform by its unique ID. This endpoint returns the platform's details, including its name, type, and key configurations. @@ -3745,12 +3943,11 @@ def get_platform( ---------- platform_id : str Platform ID. - Returns ------- Union[PlatformWeb, PlatformApple, PlatformAndroid, PlatformWindows, PlatformLinux] API response as one of the typed response models - + Raises ------ AppwriteException @@ -3761,14 +3958,17 @@ def get_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) if not isinstance(response, dict): raise AppwriteException('Expected object response when hydrating a response model') @@ -3789,10 +3989,9 @@ def get_platform( raise AppwriteException('Unable to match response to any known model') - def delete_platform( self, - platform_id: str + platform_id: str, ) -> Dict[str, Any]: """ Delete a platform by its unique ID. This endpoint removes the platform and all its configurations from the project. @@ -3801,12 +4000,11 @@ def delete_platform( ---------- platform_id : str Platform ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -3817,22 +4015,24 @@ def delete_platform( api_params = {} if platform_id is None: raise AppwriteException('Missing required parameter: "platform_id"') - api_path = api_path.replace('{platformId}', str(self._normalize_value(platform_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_policies( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> PolicyList: """ Get a list of all project policies and their current configuration. @@ -3843,12 +4043,11 @@ def list_policies( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- PolicyList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3857,23 +4056,26 @@ def list_policies( api_path = '/project/policies' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PolicyList) - def update_deny_aliased_email_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Configures if aliased emails such as subaddresses and emails with suffixes are denied during new users sign-ups and email updates. @@ -3882,12 +4084,11 @@ def update_deny_aliased_email_policy( ---------- enabled : bool Set whether or not to block aliased emails during signup and email updates. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3898,22 +4099,24 @@ def update_deny_aliased_email_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_deny_corporate_email_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Configures if only corporate email addresses (non-free and non-disposable domains) are allowed during new user sign-ups and email updates. @@ -3922,12 +4125,11 @@ def update_deny_corporate_email_policy( ---------- enabled : bool Set whether or not to restrict sign-ups and email updates to corporate email addresses only. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3938,22 +4140,24 @@ def update_deny_corporate_email_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_deny_disposable_email_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Configures if disposable emails from known temporary domains are denied during new users sign-ups and email updates. @@ -3962,12 +4166,11 @@ def update_deny_disposable_email_policy( ---------- enabled : bool Set whether or not to block disposable email addresses during signup and email updates. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3978,22 +4181,24 @@ def update_deny_disposable_email_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_deny_free_email_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Configures if emails from free providers such as Gmail or Yahoo are denied during new users sign-ups and email updates. @@ -4002,12 +4207,11 @@ def update_deny_free_email_policy( ---------- enabled : bool Set whether or not to block free email addresses during signup and email updates. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4018,19 +4222,21 @@ def update_deny_free_email_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_membership_privacy_policy( self, user_id: Optional[bool] = None, @@ -4038,7 +4244,7 @@ def update_membership_privacy_policy( user_phone: Optional[bool] = None, user_name: Optional[bool] = None, user_mfa: Optional[bool] = None, - user_accessed_at: Optional[bool] = None + user_accessed_at: Optional[bool] = None, ) -> ProjectModel: """ Updating this policy allows you to control if team members can see other members information. When enabled, all team members can see ID, name, email, phone number, and MFA status of other members.. @@ -4057,12 +4263,11 @@ def update_membership_privacy_policy( Set to true if you want make user MFA status visible to all team members, or false to hide it. user_accessed_at : Optional[bool] Set to true if you want make user last access time visible to all team members, or false to hide it. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4071,7 +4276,6 @@ def update_membership_privacy_policy( api_path = '/project/policies/membership-privacy' api_params = {} - if user_id is not None: api_params['userId'] = self._normalize_value(user_id) if user_email is not None: @@ -4085,21 +4289,25 @@ def update_membership_privacy_policy( if user_accessed_at is not None: api_params['userAccessedAt'] = self._normalize_value(user_accessed_at) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_mfa_factors_policy( self, totp: Optional[bool] = None, email: Optional[bool] = None, phone: Optional[bool] = None, - custom: Optional[bool] = None + custom: Optional[bool] = None, ) -> ProjectModel: """ Updating this policy allows you to control which factors users can use to complete an MFA challenge. Disabled factors cannot be used to create a challenge and are reported as unavailable when listing factors. The custom factor is disabled by default; enable it to deliver challenge codes through your own channel. Recovery codes always remain available as a fallback. @@ -4114,12 +4322,11 @@ def update_mfa_factors_policy( Set to true to allow phone (SMS) to complete an MFA challenge, or false to disable it. custom : Optional[bool] Set to true to allow the custom factor to complete an MFA challenge, or false to disable it. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4128,7 +4335,6 @@ def update_mfa_factors_policy( api_path = '/project/policies/mfa-factors' api_params = {} - if totp is not None: api_params['totp'] = self._normalize_value(totp) if email is not None: @@ -4138,18 +4344,22 @@ def update_mfa_factors_policy( if custom is not None: api_params['custom'] = self._normalize_value(custom) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_password_dictionary_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Updating this policy allows you to control if new passwords are checked against most common passwords dictionary. When enabled, and user changes their password, password must not be contained in the dictionary. @@ -4158,12 +4368,11 @@ def update_password_dictionary_policy( ---------- enabled : bool Toggle password dictionary policy. Set to true if you want password change to block passwords in the dictionary, or false to allow them. When changing this policy, existing passwords remain valid. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4174,38 +4383,39 @@ def update_password_dictionary_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_password_history_policy( self, - total: Optional[float] + total: Optional[float], ) -> ProjectModel: """ Updates one of password strength policies. Based on total length configured, previous password hashes are stored, and users cannot choose a new password that is already stored in the passwird history list, when updating an user password, or setting new one through password recovery. - + Keep in mind, while password history policy is disabled, the history is not being stored. Enabling the policy will not have any history on existing users, and it will only start to collect and enforce the policy on password changes since the policy is enabled. Parameters ---------- total : Optional[float] Set the password history length per user. Value can be between 1 and 20, or null to disable the limit. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4214,21 +4424,24 @@ def update_password_history_policy( api_path = '/project/policies/password-history' api_params = {} - api_params['total'] = self._normalize_value(total) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_password_personal_data_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Updating this policy allows you to control if password strength is checked against personal data. When enabled, and user sets or changes their password, the password must not contain user ID, name, email or phone number. @@ -4237,12 +4450,11 @@ def update_password_personal_data_policy( ---------- enabled : bool Toggle password personal data policy. Set to true if you want to block passwords including user's personal data, or false to allow it. When changing this policy, existing passwords remain valid. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4253,26 +4465,28 @@ def update_password_personal_data_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_password_strength_policy( self, min: Optional[float] = None, uppercase: Optional[bool] = None, lowercase: Optional[bool] = None, number: Optional[bool] = None, - symbols: Optional[bool] = None + symbols: Optional[bool] = None, ) -> PolicyPasswordStrength: """ Update the password strength requirements for users in the project. @@ -4289,12 +4503,11 @@ def update_password_strength_policy( Whether passwords must include at least one number. symbols : Optional[bool] Whether passwords must include at least one symbol. - Returns ------- PolicyPasswordStrength API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4303,7 +4516,6 @@ def update_password_strength_policy( api_path = '/project/policies/password-strength' api_params = {} - if min is not None: api_params['min'] = self._normalize_value(min) if uppercase is not None: @@ -4315,18 +4527,22 @@ def update_password_strength_policy( if symbols is not None: api_params['symbols'] = self._normalize_value(symbols) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=PolicyPasswordStrength) - def update_session_alert_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Updating this policy allows you to control if email alert is sent upon session creation. When enabled, and user signs into their account, they will be sent an email notification. There is an exception, the first session after a new sign up does not trigger an alert, even if the policy is enabled. @@ -4335,12 +4551,11 @@ def update_session_alert_policy( ---------- enabled : bool Toggle session alert policy. Set to true if you want users to receive email notifications when a sessions are created for their users, or false to not send email alerts. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4351,22 +4566,24 @@ def update_session_alert_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_session_duration_policy( self, - duration: float + duration: float, ) -> ProjectModel: """ Update maximum duration how long sessions created within a project should stay active for. @@ -4375,12 +4592,11 @@ def update_session_duration_policy( ---------- duration : float Maximum session length in seconds. Minium allowed value is 60 seconds, and maximum is 1 year, which is 31536000 seconds. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4391,22 +4607,24 @@ def update_session_duration_policy( api_params = {} if duration is None: raise AppwriteException('Missing required parameter: "duration"') - - api_params['duration'] = self._normalize_value(duration) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_session_invalidation_policy( self, - enabled: bool + enabled: bool, ) -> ProjectModel: """ Updating this policy allows you to control if existing sessions should be invalidated when a password of a user is changed. When enabled, and user changes their password, they will be logged out of all their devices. @@ -4415,12 +4633,11 @@ def update_session_invalidation_policy( ---------- enabled : bool Toggle session invalidation policy. Set to true if you want password change to invalidate all sessions of an user, or false to keep sessions active. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4431,22 +4648,24 @@ def update_session_invalidation_policy( api_params = {} if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_session_limit_policy( self, - total: float + total: float, ) -> ProjectModel: """ Update the maximum number of sessions allowed per user. When the limit is hit, the oldest session will be deleted to make room for new one. @@ -4455,12 +4674,11 @@ def update_session_limit_policy( ---------- total : float Set the maximum number of sessions allowed per user. Value can be between 1 and 100. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4471,22 +4689,24 @@ def update_session_limit_policy( api_params = {} if total is None: raise AppwriteException('Missing required parameter: "total"') - - api_params['total'] = self._normalize_value(total) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_user_limit_policy( self, - total: Optional[float] + total: Optional[float], ) -> ProjectModel: """ Update the maximum number of users in the project. When the limit is hit or amount of existing users already exceeded the limit, all users remain active, but new user sign up will be prohibited. @@ -4495,12 +4715,11 @@ def update_user_limit_policy( ---------- total : Optional[float] Set the maximum number of users allowed in the project. Value can be between 0 and 10000. Use 0 or null to disable the limit. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4509,22 +4728,41 @@ def update_user_limit_policy( api_path = '/project/policies/user-limit' api_params = {} - api_params['total'] = self._normalize_value(total) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def get_policy( self, - policy_id: ProjectPolicyId - ) -> Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail]: + policy_id: ProjectPolicyId, + ) -> Union[ + PolicyPasswordDictionary, + PolicyPasswordHistory, + PolicyPasswordStrength, + PolicyPasswordPersonalData, + PolicySessionAlert, + PolicySessionDuration, + PolicySessionInvalidation, + PolicySessionLimit, + PolicyUserLimit, + PolicyMembershipPrivacy, + PolicyMfaFactors, + PolicyDenyAliasedEmail, + PolicyDenyDisposableEmail, + PolicyDenyFreeEmail, + PolicyDenyCorporateEmail, + ]: """ Get a policy by its unique ID. This endpoint returns the current configuration for the requested project policy. @@ -4532,12 +4770,11 @@ def get_policy( ---------- policy_id : ProjectPolicyId Policy ID. Can be one of: password-dictionary, password-history, password-strength, password-personal-data, session-alert, session-duration, session-invalidation, session-limit, user-limit, membership-privacy, mfa-factors, deny-aliased-email, deny-disposable-email, deny-free-email, deny-corporate-email. - Returns ------- Union[PolicyPasswordDictionary, PolicyPasswordHistory, PolicyPasswordStrength, PolicyPasswordPersonalData, PolicySessionAlert, PolicySessionDuration, PolicySessionInvalidation, PolicySessionLimit, PolicyUserLimit, PolicyMembershipPrivacy, PolicyMfaFactors, PolicyDenyAliasedEmail, PolicyDenyDisposableEmail, PolicyDenyFreeEmail, PolicyDenyCorporateEmail] API response as one of the typed response models - + Raises ------ AppwriteException @@ -4548,14 +4785,17 @@ def get_policy( api_params = {} if policy_id is None: raise AppwriteException('Missing required parameter: "policy_id"') - api_path = api_path.replace('{policyId}', str(self._normalize_value(policy_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) if not isinstance(response, dict): raise AppwriteException('Expected object response when hydrating a response model') @@ -4606,14 +4846,13 @@ def get_policy( raise AppwriteException('Unable to match response to any known model') - def update_protocol( self, protocol_id: ProjectProtocolId, - enabled: bool + enabled: bool, ) -> ProjectModel: """ - Update properties of a specific protocol. Use this endpoint to enable or disable a protocol in your project. + Update properties of a specific protocol. Use this endpoint to enable or disable a protocol in your project. Parameters ---------- @@ -4621,12 +4860,11 @@ def update_protocol( Protocol name. Can be one of: rest, graphql, websocket enabled : bool Protocol status. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4637,30 +4875,31 @@ def update_protocol( api_params = {} if protocol_id is None: raise AppwriteException('Missing required parameter: "protocol_id"') - if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - api_path = api_path.replace('{protocolId}', str(self._normalize_value(protocol_id))) - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_service( self, service_id: ProjectServiceId, - enabled: bool + enabled: bool, ) -> ProjectModel: """ - Update properties of a specific service. Use this endpoint to enable or disable a service in your project. + Update properties of a specific service. Use this endpoint to enable or disable a service in your project. Parameters ---------- @@ -4668,12 +4907,11 @@ def update_service( Service name. Can be one of: account, avatars, databases, tablesdb, locale, health, project, storage, teams, users, vcs, sites, functions, proxy, graphql, migrations, messaging, advisor, oauth2 enabled : bool Service status. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4684,23 +4922,24 @@ def update_service( api_params = {} if service_id is None: raise AppwriteException('Missing required parameter: "service_id"') - if enabled is None: raise AppwriteException('Missing required parameter: "enabled"') - api_path = api_path.replace('{serviceId}', str(self._normalize_value(service_id))) - api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def update_smtp( self, host: Optional[str] = None, @@ -4712,7 +4951,7 @@ def update_smtp( reply_to_email: Optional[str] = None, reply_to_name: Optional[str] = None, secure: Optional[ProjectSMTPSecure] = None, - enabled: Optional[bool] = None + enabled: Optional[bool] = None, ) -> ProjectModel: """ Update the SMTP configuration for your project. Use this endpoint to configure your project's SMTP provider with your custom settings for sending transactional emails. @@ -4739,12 +4978,11 @@ def update_smtp( Configures if communication with SMTP server is encrypted. Allowed values are: tls, ssl. Leave empty for no encryption. enabled : Optional[bool] Enable or disable custom SMTP. Custom SMTP is useful for branding purposes, but also allows use of custom email templates. - Returns ------- ProjectModel API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4753,7 +4991,6 @@ def update_smtp( api_path = '/project/smtp' api_params = {} - if host is not None: api_params['host'] = self._normalize_value(host) if port is not None: @@ -4775,32 +5012,35 @@ def update_smtp( if enabled is not None: api_params['enabled'] = self._normalize_value(enabled) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProjectModel) - def create_smtp_test( self, - emails: List[str] + emails: List[str], ) -> Dict[str, Any]: """ - Send a test email to verify SMTP configuration. + Send a test email to verify SMTP configuration. Parameters ---------- emails : List[str] Array of emails to send test email to. Maximum of 10 emails are allowed. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -4811,22 +5051,24 @@ def create_smtp_test( api_params = {} if emails is None: raise AppwriteException('Missing required parameter: "emails"') - - api_params['emails'] = self._normalize_value(emails) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_email_templates( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> EmailTemplateList: """ Get a list of all custom email templates configured for the project. This endpoint returns an array of all configured email templates and their locales. @@ -4837,12 +5079,11 @@ def list_email_templates( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- EmailTemplateList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4851,20 +5092,23 @@ def list_email_templates( api_path = '/project/templates/email' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=EmailTemplateList) - def update_email_template( self, template_id: ProjectEmailTemplateId, @@ -4874,7 +5118,7 @@ def update_email_template( sender_name: Optional[str] = None, sender_email: Optional[str] = None, reply_to_email: Optional[str] = None, - reply_to_name: Optional[str] = None + reply_to_name: Optional[str] = None, ) -> EmailTemplate: """ Update a custom email template for the specified locale and type. Use this endpoint to modify the content of your email templates. @@ -4897,12 +5141,11 @@ def update_email_template( Reply to email. Pass an empty string to clear a previously set value. reply_to_name : Optional[str] Reply to name. - Returns ------- EmailTemplate API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4913,8 +5156,6 @@ def update_email_template( api_params = {} if template_id is None: raise AppwriteException('Missing required parameter: "template_id"') - - api_params['templateId'] = self._normalize_value(template_id) if locale is not None: api_params['locale'] = self._normalize_value(locale) @@ -4931,19 +5172,23 @@ def update_email_template( if reply_to_name is not None: api_params['replyToName'] = self._normalize_value(reply_to_name) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=EmailTemplate) - def get_email_template( self, template_id: ProjectEmailTemplateId, - locale: Optional[ProjectEmailTemplateLocale] = None + locale: Optional[ProjectEmailTemplateLocale] = None, ) -> EmailTemplate: """ Get a custom email template for the specified locale and type. This endpoint returns the template content, subject, and other configuration details. @@ -4954,12 +5199,11 @@ def get_email_template( Custom email template type. Can be one of: verification, magicSession, recovery, invitation, mfaChallenge, sessionAlert, otpSession locale : Optional[ProjectEmailTemplateLocale] Custom email template locale. If left empty, the fallback locale (en) will be used. - Returns ------- EmailTemplate API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4970,24 +5214,26 @@ def get_email_template( api_params = {} if template_id is None: raise AppwriteException('Missing required parameter: "template_id"') - api_path = api_path.replace('{templateId}', str(self._normalize_value(template_id))) - if locale is not None: api_params['locale'] = self._normalize_value(locale) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=EmailTemplate) - def list_variables( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> VariableList: """ Get a list of all project environment variables. @@ -4998,12 +5244,11 @@ def list_variables( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, resourceType, resourceId, secret total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- VariableList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5012,26 +5257,29 @@ def list_variables( api_path = '/project/variables' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=VariableList) - def create_variable( self, variable_id: str, key: str, value: str, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Create a new project environment variable. These variables can be accessed by all functions and sites in the project. @@ -5041,17 +5289,16 @@ def create_variable( variable_id : str Variable unique ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. key : str - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : str Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only projects can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5062,46 +5309,45 @@ def create_variable( api_params = {} if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if value is None: raise AppwriteException('Missing required parameter: "value"') - - api_params['variableId'] = self._normalize_value(variable_id) api_params['key'] = self._normalize_value(key) api_params['value'] = self._normalize_value(value) if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def get_variable( self, - variable_id: str + variable_id: str, ) -> Variable: """ - Get a variable by its unique ID. + Get a variable by its unique ID. Parameters ---------- variable_id : str Variable unique ID. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5112,24 +5358,26 @@ def get_variable( api_params = {} if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def update_variable( self, variable_id: str, key: Optional[str] = None, value: Optional[str] = None, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Update variable by its unique ID. @@ -5139,17 +5387,16 @@ def update_variable( variable_id : str Variable unique ID. key : Optional[str] - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : Optional[str] Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only projects can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5160,9 +5407,7 @@ def update_variable( api_params = {} if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - if key is not None: api_params['key'] = self._normalize_value(key) if value is not None: @@ -5170,32 +5415,35 @@ def update_variable( if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def delete_variable( self, - variable_id: str + variable_id: str, ) -> Dict[str, Any]: """ - Delete a variable by its unique ID. + Delete a variable by its unique ID. Parameters ---------- variable_id : str Variable unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -5206,14 +5454,16 @@ def delete_variable( api_params = {} if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/proxy.py b/appwrite/services/proxy.py index ce209139..0429a4e9 100644 --- a/appwrite/services/proxy.py +++ b/appwrite/services/proxy.py @@ -10,6 +10,7 @@ from ..enums.status_code import StatusCode from ..enums.proxy_resource_type import ProxyResourceType + class Proxy(Service): def __init__(self, client) -> None: @@ -19,11 +20,11 @@ def create_invalidation( self, domain: str, type: InvalidationType, - reference: Optional[str] = None + reference: Optional[str] = None, ) -> ProxyInvalidation: """ Create a new CDN cache invalidation for a domain. Executes a hard purge of cached content. - + Depending on type, the invalidation purges a single cache tag, a single URL path, or all cached content for the domain. Parameters @@ -34,12 +35,11 @@ def create_invalidation( Type of reference passed. Allowed values are: tag, path, all reference : Optional[str] Reference to invalidate. Depending on type this can be: cache tag name (up to 128 characters), URL path (up to 2048 characters). Not required when type is all. - Returns ------- ProxyInvalidation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -50,29 +50,30 @@ def create_invalidation( api_params = {} if domain is None: raise AppwriteException('Missing required parameter: "domain"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - - api_params['domain'] = self._normalize_value(domain) api_params['type'] = self._normalize_value(type) if reference is not None: api_params['reference'] = self._normalize_value(reference) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyInvalidation) - def list_rules( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ProxyRuleList: """ Get a list of all the proxy rules. You can use the query params to filter your results. @@ -83,12 +84,11 @@ def list_rules( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/databases#querying-documents). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: domain, type, trigger, deploymentResourceType, deploymentResourceId, deploymentId, deploymentVcsProviderBranch total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ProxyRuleList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -97,39 +97,41 @@ def list_rules( api_path = '/proxy/rules' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRuleList) - def create_api_rule( self, - domain: str + domain: str, ) -> ProxyRule: """ Create a new proxy rule for serving Appwrite's API on custom domain. - + Rule ID is automatically generated as MD5 hash of a rule domain for performance purposes. Parameters ---------- domain : str Domain name. - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -140,28 +142,30 @@ def create_api_rule( api_params = {} if domain is None: raise AppwriteException('Missing required parameter: "domain"') - - api_params['domain'] = self._normalize_value(domain) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - def create_function_rule( self, domain: str, function_id: str, - branch: Optional[str] = None + branch: Optional[str] = None, ) -> ProxyRule: """ Create a new proxy rule for executing Appwrite Function on custom domain. - + Rule ID is automatically generated as MD5 hash of a rule domain for performance purposes. Parameters @@ -172,12 +176,11 @@ def create_function_rule( ID of function to be executed. branch : Optional[str] Name of VCS branch to deploy changes automatically - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -188,36 +191,37 @@ def create_function_rule( api_params = {} if domain is None: raise AppwriteException('Missing required parameter: "domain"') - if function_id is None: raise AppwriteException('Missing required parameter: "function_id"') - - api_params['domain'] = self._normalize_value(domain) api_params['functionId'] = self._normalize_value(function_id) if branch is not None: api_params['branch'] = self._normalize_value(branch) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - def create_redirect_rule( self, domain: str, url: str, status_code: StatusCode, resource_id: str, - resource_type: ProxyResourceType + resource_type: ProxyResourceType, ) -> ProxyRule: """ Create a new proxy rule for to redirect from custom domain to another domain. - + Rule ID is automatically generated as MD5 hash of a rule domain for performance purposes. Parameters @@ -232,12 +236,11 @@ def create_redirect_rule( ID of parent resource. resource_type : ProxyResourceType Type of parent resource. - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -248,44 +251,42 @@ def create_redirect_rule( api_params = {} if domain is None: raise AppwriteException('Missing required parameter: "domain"') - if url is None: raise AppwriteException('Missing required parameter: "url"') - if status_code is None: raise AppwriteException('Missing required parameter: "status_code"') - if resource_id is None: raise AppwriteException('Missing required parameter: "resource_id"') - if resource_type is None: raise AppwriteException('Missing required parameter: "resource_type"') - - api_params['domain'] = self._normalize_value(domain) api_params['url'] = self._normalize_value(url) api_params['statusCode'] = self._normalize_value(status_code) api_params['resourceId'] = self._normalize_value(resource_id) api_params['resourceType'] = self._normalize_value(resource_type) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - def create_site_rule( self, domain: str, site_id: str, - branch: Optional[str] = None + branch: Optional[str] = None, ) -> ProxyRule: """ Create a new proxy rule for serving Appwrite Site on custom domain. - + Rule ID is automatically generated as MD5 hash of a rule domain for performance purposes. Parameters @@ -296,12 +297,11 @@ def create_site_rule( ID of site to be executed. branch : Optional[str] Name of VCS branch to deploy changes automatically - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -312,28 +312,29 @@ def create_site_rule( api_params = {} if domain is None: raise AppwriteException('Missing required parameter: "domain"') - if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - - api_params['domain'] = self._normalize_value(domain) api_params['siteId'] = self._normalize_value(site_id) if branch is not None: api_params['branch'] = self._normalize_value(branch) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - def get_rule( self, - rule_id: str + rule_id: str, ) -> ProxyRule: """ Get a proxy rule by its unique ID. @@ -342,12 +343,11 @@ def get_rule( ---------- rule_id : str Rule ID. - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -358,21 +358,23 @@ def get_rule( api_params = {} if rule_id is None: raise AppwriteException('Missing required parameter: "rule_id"') - api_path = api_path.replace('{ruleId}', str(self._normalize_value(rule_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - def delete_rule( self, - rule_id: str + rule_id: str, ) -> Dict[str, Any]: """ Delete a proxy rule by its unique ID. @@ -381,12 +383,11 @@ def delete_rule( ---------- rule_id : str Rule ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -397,21 +398,23 @@ def delete_rule( api_params = {} if rule_id is None: raise AppwriteException('Missing required parameter: "rule_id"') - api_path = api_path.replace('{ruleId}', str(self._normalize_value(rule_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_rule_status( self, - rule_id: str + rule_id: str, ) -> ProxyRule: """ If not succeeded yet, retry verification process of a proxy rule domain. This endpoint triggers domain verification by checking DNS records. If verification is successful, a TLS certificate will be automatically provisioned for the domain asynchronously in the background. @@ -420,12 +423,11 @@ def update_rule_status( ---------- rule_id : str Rule ID. - Returns ------- ProxyRule API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -436,15 +438,17 @@ def update_rule_status( api_params = {} if rule_id is None: raise AppwriteException('Missing required parameter: "rule_id"') - api_path = api_path.replace('{ruleId}', str(self._normalize_value(rule_id))) - - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ProxyRule) - diff --git a/appwrite/services/sites.py b/appwrite/services/sites.py index 8b930f17..36a29462 100644 --- a/appwrite/services/sites.py +++ b/appwrite/services/sites.py @@ -7,6 +7,7 @@ from ..enums.framework import Framework from ..enums.build_runtime import BuildRuntime from ..enums.adapter import Adapter +from ..enums.project_key_scopes import ProjectKeyScopes from ..models.site import Site from ..models.framework_list import FrameworkList from ..models.specification_list import SpecificationList @@ -21,6 +22,7 @@ from ..models.variable_list import VariableList from ..models.variable import Variable + class Sites(Service): def __init__(self, client) -> None: @@ -30,7 +32,7 @@ def list( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> SiteList: """ Get a list of all the project's sites. You can use the query params to filter your results. @@ -43,12 +45,11 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- SiteList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -57,7 +58,6 @@ def list( api_path = '/sites' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -65,14 +65,18 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SiteList) - def create( self, site_id: str, @@ -97,7 +101,8 @@ def create( provider_paths: Optional[List[str]] = None, build_specification: Optional[str] = None, runtime_specification: Optional[str] = None, - deployment_retention: Optional[float] = None + deployment_retention: Optional[float] = None, + scopes: Optional[List[ProjectKeyScopes]] = None, ) -> Site: """ Create a new site. @@ -150,12 +155,13 @@ def create( Runtime specification for the SSR executions. deployment_retention : Optional[float] Days to keep non-active deployments before deletion. Value 0 means all deployments will be kept. - + scopes : Optional[List[ProjectKeyScopes]] + List of scopes allowed for API key auto-generated for every site build and SSR execution. Maximum of 200 scopes are allowed. Returns ------- Site API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -166,17 +172,12 @@ def create( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if framework is None: raise AppwriteException('Missing required parameter: "framework"') - if build_runtime is None: raise AppwriteException('Missing required parameter: "build_runtime"') - - api_params['siteId'] = self._normalize_value(site_id) api_params['name'] = self._normalize_value(name) api_params['framework'] = self._normalize_value(framework) @@ -219,27 +220,32 @@ def create( api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: api_params['deploymentRetention'] = self._normalize_value(deployment_retention) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + if scopes is not None: + api_params['scopes'] = self._normalize_value(scopes) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Site) - def list_frameworks( - self + self, ) -> FrameworkList: """ Get a list of all frameworks that are currently available on the server instance. - Returns ------- FrameworkList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -249,17 +255,21 @@ def list_frameworks( api_path = '/sites/frameworks' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=FrameworkList) - def list_specifications( self, - type: Optional[str] = None + type: Optional[str] = None, ) -> SpecificationList: """ List allowed site specifications for this instance. @@ -268,12 +278,11 @@ def list_specifications( ---------- type : Optional[str] Specification type to list. Can be one of: runtimes, builds. Defaults to runtimes. - Returns ------- SpecificationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -282,21 +291,24 @@ def list_specifications( api_path = '/sites/specifications' api_params = {} - if type is not None: api_params['type'] = self._normalize_value(type) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SpecificationList) - def get( self, - site_id: str + site_id: str, ) -> Site: """ Get a site by its unique ID. @@ -305,12 +317,11 @@ def get( ---------- site_id : str Site ID. - Returns ------- Site API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -321,18 +332,20 @@ def get( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Site) - def update( self, site_id: str, @@ -357,7 +370,8 @@ def update( provider_paths: Optional[List[str]] = None, build_specification: Optional[str] = None, runtime_specification: Optional[str] = None, - deployment_retention: Optional[float] = None + deployment_retention: Optional[float] = None, + scopes: Optional[List[ProjectKeyScopes]] = None, ) -> Site: """ Update site by its unique ID. @@ -410,12 +424,13 @@ def update( Runtime specification for the SSR executions. deployment_retention : Optional[float] Days to keep non-active deployments before deletion. Value 0 means all deployments will be kept. - + scopes : Optional[List[ProjectKeyScopes]] + List of scopes allowed for API key auto-generated for every site build and SSR execution. Maximum of 200 scopes are allowed. Returns ------- Site API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -426,15 +441,11 @@ def update( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if framework is None: raise AppwriteException('Missing required parameter: "framework"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['name'] = self._normalize_value(name) api_params['framework'] = self._normalize_value(framework) if enabled is not None: @@ -477,19 +488,25 @@ def update( api_params['runtimeSpecification'] = self._normalize_value(runtime_specification) if deployment_retention is not None: api_params['deploymentRetention'] = self._normalize_value(deployment_retention) - - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + if scopes is not None: + api_params['scopes'] = self._normalize_value(scopes) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Site) - def delete( self, - site_id: str + site_id: str, ) -> Dict[str, Any]: """ Delete a site by its unique ID. @@ -498,12 +515,11 @@ def delete( ---------- site_id : str Site ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -514,22 +530,24 @@ def delete( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_site_deployment( self, site_id: str, - deployment_id: str + deployment_id: str, ) -> Site: """ Update the site active deployment. Use this endpoint to switch the code deployment that should be used when visitor opens your site. @@ -540,12 +558,11 @@ def update_site_deployment( Site ID. deployment_id : str Deployment ID. - Returns ------- Site API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -556,29 +573,30 @@ def update_site_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['deploymentId'] = self._normalize_value(deployment_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Site) - def list_deployments( self, site_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> DeploymentList: """ Get a list of all the site's code deployments. You can use the query params to filter your results. @@ -593,12 +611,11 @@ def list_deployments( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- DeploymentList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -609,9 +626,7 @@ def list_deployments( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -619,14 +634,18 @@ def list_deployments( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DeploymentList) - def create_deployment( self, site_id: str, @@ -635,7 +654,7 @@ def create_deployment( build_command: Optional[str] = None, output_directory: Optional[str] = None, activate: Optional[bool] = None, - on_progress = None + on_progress=None, ) -> Deployment: """ Create a new site code deployment. Use this endpoint to upload a new version of your site code. To activate your newly uploaded code, you'll need to update the site's deployment to use your new deployment ID. @@ -654,14 +673,14 @@ def create_deployment( Output Directory. activate : Optional[bool] Automatically activate the deployment when it is finished building. - on_progress : callable, optional + on_progress : callable, optional Optional callback for upload progress - + Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -672,12 +691,9 @@ def create_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if code is None: raise AppwriteException('Missing required parameter: "code"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - if install_command is not None: api_params['installCommand'] = self._normalize_value(install_command) if build_command is not None: @@ -686,26 +702,33 @@ def create_deployment( api_params['outputDirectory'] = self._normalize_value(output_directory) api_params['code'] = self._normalize_value(code) if activate is not None: - api_params['activate'] = self._normalize_value(str(activate).lower() if type(activate) is bool else activate) + api_params['activate'] = self._normalize_value( + str(activate).lower() if type(activate) is bool else activate, + ) param_name = 'code' - upload_id = '' - response = self.client.chunked_upload(api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'multipart/form-data', - 'accept': 'application/json', - }, api_params, param_name, on_progress, upload_id) + response = self.client.chunked_upload( + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'multipart/form-data', + 'accept': 'application/json', + }, + api_params, + param_name, + on_progress, + upload_id, + ) return self._parse_response(response, model=Deployment) - def create_duplicate_deployment( self, site_id: str, - deployment_id: str + deployment_id: str, ) -> Deployment: """ Create a new build for an existing site deployment. This endpoint allows you to rebuild a deployment with the updated site configuration, including its commands and output directory if they have been modified. The build process will be queued and executed asynchronously. The original deployment's code will be preserved and used for the new build. @@ -716,12 +739,11 @@ def create_duplicate_deployment( Site ID. deployment_id : str Deployment ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -732,23 +754,24 @@ def create_duplicate_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['deploymentId'] = self._normalize_value(deployment_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def create_template_deployment( self, site_id: str, @@ -757,11 +780,11 @@ def create_template_deployment( root_directory: str, type: TemplateReferenceType, reference: str, - activate: Optional[bool] = None + activate: Optional[bool] = None, ) -> Deployment: """ Create a deployment based on a template. - + Use this endpoint with combination of [listTemplates](https://appwrite.io/docs/products/sites/templates) to find the template details. Parameters @@ -780,12 +803,11 @@ def create_template_deployment( Reference value, can be a commit hash, branch name, or release tag activate : Optional[bool] Automatically activate the deployment when it is finished building. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -796,24 +818,17 @@ def create_template_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if repository is None: raise AppwriteException('Missing required parameter: "repository"') - if owner is None: raise AppwriteException('Missing required parameter: "owner"') - if root_directory is None: raise AppwriteException('Missing required parameter: "root_directory"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if reference is None: raise AppwriteException('Missing required parameter: "reference"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['repository'] = self._normalize_value(repository) api_params['owner'] = self._normalize_value(owner) api_params['rootDirectory'] = self._normalize_value(root_directory) @@ -822,25 +837,29 @@ def create_template_deployment( if activate is not None: api_params['activate'] = self._normalize_value(activate) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def create_vcs_deployment( self, site_id: str, type: VCSReferenceType, reference: str, - activate: Optional[bool] = None + activate: Optional[bool] = None, ) -> Deployment: """ Create a deployment when a site is connected to VCS. - + This endpoint lets you create deployment from a branch, commit, or a tag. Parameters @@ -853,12 +872,11 @@ def create_vcs_deployment( VCS reference to create deployment from. Depending on type this can be: branch name, commit hash activate : Optional[bool] Automatically activate the deployment when it is finished building. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -869,33 +887,33 @@ def create_vcs_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if reference is None: raise AppwriteException('Missing required parameter: "reference"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['type'] = self._normalize_value(type) api_params['reference'] = self._normalize_value(reference) if activate is not None: api_params['activate'] = self._normalize_value(activate) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def get_deployment( self, site_id: str, - deployment_id: str + deployment_id: str, ) -> Deployment: """ Get a site deployment by its unique ID. @@ -906,12 +924,11 @@ def get_deployment( Site ID. deployment_id : str Deployment ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -922,26 +939,27 @@ def get_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def delete_deployment( self, site_id: str, - deployment_id: str + deployment_id: str, ) -> Dict[str, Any]: """ Delete a site deployment by its unique ID. @@ -952,12 +970,11 @@ def delete_deployment( Site ID. deployment_id : str Deployment ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -968,28 +985,29 @@ def delete_deployment( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def get_deployment_download( self, site_id: str, deployment_id: str, type: Optional[DeploymentDownloadType] = None, - token: Optional[str] = None + token: Optional[str] = None, ) -> bytes: """ Get a site deployment content by its unique ID. The endpoint response return with a 'Content-Disposition: attachment' header that tells the browser to start downloading the file to user downloads directory. @@ -1004,12 +1022,11 @@ def get_deployment_download( Deployment file to download. Can be: "source", "output". token : Optional[str] Presigned source-download token for accessing this deployment without a session (jobs-service). - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -1020,30 +1037,31 @@ def get_deployment_download( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - if type is not None: api_params['type'] = self._normalize_value(type) if token is not None: api_params['token'] = self._normalize_value(token) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': '*/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': '*/*', + }, + api_params, + ) return response - def update_deployment_status( self, site_id: str, - deployment_id: str + deployment_id: str, ) -> Deployment: """ Cancel an ongoing site deployment build. If the build is already in progress, it will be stopped and marked as canceled. If the build hasn't started yet, it will be marked as canceled without executing. You cannot cancel builds that have already completed (status 'ready') or failed. The response includes the final build status and details. @@ -1054,12 +1072,11 @@ def update_deployment_status( Site ID. deployment_id : str Deployment ID. - Returns ------- Deployment API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1070,28 +1087,29 @@ def update_deployment_status( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if deployment_id is None: raise AppwriteException('Missing required parameter: "deployment_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{deploymentId}', str(self._normalize_value(deployment_id))) - - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Deployment) - def list_logs( self, site_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ExecutionList: """ Get a list of all site logs. You can use the query params to filter your results. @@ -1104,12 +1122,11 @@ def list_logs( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: trigger, status, responseStatusCode, duration, requestMethod, requestPath, deploymentId total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ExecutionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1120,26 +1137,28 @@ def list_logs( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ExecutionList) - def get_log( self, site_id: str, - log_id: str + log_id: str, ) -> Execution: """ Get a site request log by its unique ID. @@ -1150,12 +1169,11 @@ def get_log( Site ID. log_id : str Log ID. - Returns ------- Execution API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1166,26 +1184,27 @@ def get_log( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if log_id is None: raise AppwriteException('Missing required parameter: "log_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{logId}', str(self._normalize_value(log_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Execution) - def delete_log( self, site_id: str, - log_id: str + log_id: str, ) -> Dict[str, Any]: """ Delete a site log by its unique ID. @@ -1196,12 +1215,11 @@ def delete_log( Site ID. log_id : str Log ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1212,28 +1230,29 @@ def delete_log( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if log_id is None: raise AppwriteException('Missing required parameter: "log_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{logId}', str(self._normalize_value(log_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_variables( self, site_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> VariableList: """ Get a list of all variables of a specific site. @@ -1246,12 +1265,11 @@ def list_variables( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, resourceType, resourceId, secret total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- VariableList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1262,29 +1280,31 @@ def list_variables( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=VariableList) - def create_variable( self, site_id: str, variable_id: str, key: str, value: str, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Create a new site variable. These variables can be accessed during build and runtime (server-side rendering) as environment variables. @@ -1296,17 +1316,16 @@ def create_variable( variable_id : str Variable ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. key : str - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : str Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only sites can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1317,37 +1336,36 @@ def create_variable( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if value is None: raise AppwriteException('Missing required parameter: "value"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) - api_params['variableId'] = self._normalize_value(variable_id) api_params['key'] = self._normalize_value(key) api_params['value'] = self._normalize_value(value) if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def get_variable( self, site_id: str, - variable_id: str + variable_id: str, ) -> Variable: """ Get a variable by its unique ID. @@ -1358,12 +1376,11 @@ def get_variable( Site unique ID. variable_id : str Variable unique ID. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1374,29 +1391,30 @@ def get_variable( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def update_variable( self, site_id: str, variable_id: str, key: Optional[str] = None, value: Optional[str] = None, - secret: Optional[bool] = None + secret: Optional[bool] = None, ) -> Variable: """ Update variable by its unique ID. @@ -1408,17 +1426,16 @@ def update_variable( variable_id : str Variable unique ID. key : Optional[str] - Variable key. Max length: 255 chars. + Variable key. Letters, digits and underscores only, must not start with a digit. Max length: 255 chars. value : Optional[str] Variable value. Max length: 8192 chars. secret : Optional[bool] Secret variables can be updated or deleted, but only sites can read them during build and runtime. - Returns ------- Variable API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1429,13 +1446,10 @@ def update_variable( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - if key is not None: api_params['key'] = self._normalize_value(key) if value is not None: @@ -1443,19 +1457,23 @@ def update_variable( if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Variable) - def delete_variable( self, site_id: str, - variable_id: str + variable_id: str, ) -> Dict[str, Any]: """ Delete a variable by its unique ID. @@ -1466,12 +1484,11 @@ def delete_variable( Site unique ID. variable_id : str Variable unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1482,18 +1499,19 @@ def delete_variable( api_params = {} if site_id is None: raise AppwriteException('Missing required parameter: "site_id"') - if variable_id is None: raise AppwriteException('Missing required parameter: "variable_id"') - api_path = api_path.replace('{siteId}', str(self._normalize_value(site_id))) api_path = api_path.replace('{variableId}', str(self._normalize_value(variable_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/storage.py b/appwrite/services/storage.py index 7511db08..7e4f647d 100644 --- a/appwrite/services/storage.py +++ b/appwrite/services/storage.py @@ -12,6 +12,7 @@ from ..enums.image_gravity import ImageGravity from ..enums.image_format import ImageFormat + class Storage(Service): def __init__(self, client) -> None: @@ -21,7 +22,7 @@ def list_buckets( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> BucketList: """ Get a list of all the storage buckets. You can use the query params to filter your results. @@ -34,12 +35,11 @@ def list_buckets( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- BucketList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -48,7 +48,6 @@ def list_buckets( api_path = '/storage/buckets' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -56,14 +55,18 @@ def list_buckets( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=BucketList) - def create_bucket( self, bucket_id: str, @@ -76,7 +79,7 @@ def create_bucket( compression: Optional[Compression] = None, encryption: Optional[bool] = None, antivirus: Optional[bool] = None, - transformations: Optional[bool] = None + transformations: Optional[bool] = None, ) -> Bucket: """ Create a new storage bucket. @@ -105,12 +108,11 @@ def create_bucket( Is virus scanning enabled? For file size above 20MB AntiVirus scanning is skipped even if it's enabled transformations : Optional[bool] Are image transformations enabled? - Returns ------- Bucket API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -121,11 +123,8 @@ def create_bucket( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['bucketId'] = self._normalize_value(bucket_id) api_params['name'] = self._normalize_value(name) if permissions is not None: @@ -147,18 +146,22 @@ def create_bucket( if transformations is not None: api_params['transformations'] = self._normalize_value(transformations) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Bucket) - def get_bucket( self, - bucket_id: str + bucket_id: str, ) -> Bucket: """ Get a storage bucket by its unique ID. This endpoint response returns a JSON object with the storage bucket metadata. @@ -167,12 +170,11 @@ def get_bucket( ---------- bucket_id : str Bucket unique ID. - Returns ------- Bucket API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -183,18 +185,20 @@ def get_bucket( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Bucket) - def update_bucket( self, bucket_id: str, @@ -207,7 +211,7 @@ def update_bucket( compression: Optional[Compression] = None, encryption: Optional[bool] = None, antivirus: Optional[bool] = None, - transformations: Optional[bool] = None + transformations: Optional[bool] = None, ) -> Bucket: """ Update a storage bucket by its unique ID. @@ -236,12 +240,11 @@ def update_bucket( Is virus scanning enabled? For file size above 20MB AntiVirus scanning is skipped even if it's enabled transformations : Optional[bool] Are image transformations enabled? - Returns ------- Bucket API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -252,12 +255,9 @@ def update_bucket( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) - api_params['name'] = self._normalize_value(name) if permissions is not None: api_params['permissions'] = self._normalize_value(permissions) @@ -278,18 +278,22 @@ def update_bucket( if transformations is not None: api_params['transformations'] = self._normalize_value(transformations) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Bucket) - def delete_bucket( self, - bucket_id: str + bucket_id: str, ) -> Dict[str, Any]: """ Delete a storage bucket by its unique ID. @@ -298,12 +302,11 @@ def delete_bucket( ---------- bucket_id : str Bucket unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -314,24 +317,26 @@ def delete_bucket( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_files( self, bucket_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> FileList: """ Get a list of all the user files. You can use the query params to filter your results. @@ -346,12 +351,11 @@ def list_files( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- FileList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -362,9 +366,7 @@ def list_files( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -372,14 +374,18 @@ def list_files( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=FileList) - def create_file( self, bucket_id: str, @@ -387,17 +393,16 @@ def create_file( file: InputFile, permissions: Optional[List[str]] = None, folder: Optional[str] = None, - on_progress = None + on_progress=None, ) -> File: """ Create a new file. Before using this route, you should create a new bucket resource using either a [server integration](https://appwrite.io/docs/server/storage#storageCreateBucket) API or directly from your Appwrite console. - + Larger files should be uploaded using multiple requests with the [content-range](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Range) header to send a partial request with a maximum supported chunk of `5MB`. The `content-range` header values should always be in bytes. - + When the first request is sent, the server will return the **File** object, and the subsequent part request must include the file's **id** in `x-appwrite-id` header to allow the server to know that the partial upload is for the existing file and not for a new one. - + If you're creating a new file using one of the Appwrite SDKs, all the chunking logic will be managed by the SDK internally. - Parameters ---------- @@ -411,14 +416,14 @@ def create_file( An array of permission strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). folder : Optional[str] Virtual folder to place the file in, for example "photos/2026". Nest folders with `/`. Defaults to the bucket root. - on_progress : callable, optional + on_progress : callable, optional Optional callback for upload progress - + Returns ------- File API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -429,15 +434,11 @@ def create_file( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - if file is None: raise AppwriteException('Missing required parameter: "file"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) - api_params['fileId'] = self._normalize_value(file_id) api_params['file'] = self._normalize_value(file) if permissions is not None: @@ -447,23 +448,28 @@ def create_file( param_name = 'file' - upload_id = '' upload_id = file_id - response = self.client.chunked_upload(api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'multipart/form-data', - 'accept': 'application/json', - }, api_params, param_name, on_progress, upload_id) + response = self.client.chunked_upload( + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'multipart/form-data', + 'accept': 'application/json', + }, + api_params, + param_name, + on_progress, + upload_id, + ) return self._parse_response(response, model=File) - def get_file( self, bucket_id: str, - file_id: str + file_id: str, ) -> File: """ Get a file by its unique ID. This endpoint response returns a JSON object with the file metadata. @@ -474,12 +480,11 @@ def get_file( Storage bucket unique ID. You can create a new storage bucket using the Storage service [server integration](https://appwrite.io/docs/server/storage#createBucket). file_id : str File ID. - Returns ------- File API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -490,28 +495,29 @@ def get_file( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=File) - def update_file( self, bucket_id: str, file_id: str, name: Optional[str] = None, - permissions: Optional[List[str]] = None + permissions: Optional[List[str]] = None, ) -> File: """ Update a file by its unique ID. Only users with write permissions have access to update this resource. @@ -526,12 +532,11 @@ def update_file( File name. permissions : Optional[List[str]] An array of permission strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). - Returns ------- File API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -542,31 +547,32 @@ def update_file( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if permissions is not None: api_params['permissions'] = self._normalize_value(permissions) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=File) - def delete_file( self, bucket_id: str, - file_id: str + file_id: str, ) -> Dict[str, Any]: """ Delete a file by its unique ID. Only users with write permissions have access to delete this resource. @@ -577,12 +583,11 @@ def delete_file( Storage bucket unique ID. You can create a new storage bucket using the Storage service [server integration](https://appwrite.io/docs/server/storage#createBucket). file_id : str File ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -593,27 +598,28 @@ def delete_file( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def get_file_download( self, bucket_id: str, file_id: str, - token: Optional[str] = None + token: Optional[str] = None, ) -> bytes: """ Get a file content by its unique ID. The endpoint response return with a 'Content-Disposition: attachment' header that tells the browser to start downloading the file to user downloads directory. @@ -626,12 +632,11 @@ def get_file_download( File ID. token : Optional[str] File token for accessing this file. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -642,24 +647,25 @@ def get_file_download( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if token is not None: api_params['token'] = self._normalize_value(token) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': '*/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': '*/*', + }, + api_params, + ) return response - def get_file_preview( self, bucket_id: str, @@ -675,7 +681,7 @@ def get_file_preview( rotation: Optional[float] = None, background: Optional[str] = None, output: Optional[ImageFormat] = None, - token: Optional[str] = None + token: Optional[str] = None, ) -> bytes: """ Get a file preview image. Currently, this method supports preview for image files (jpg, png, and gif), other supported formats, like pdf, docs, slides, and spreadsheets, will return the file icon image. You can also pass query string arguments for cutting and resizing your preview image. Preview is supported only for image files smaller than 10MB. @@ -710,12 +716,11 @@ def get_file_preview( Output format type (jpeg, jpg, png, gif and webp). token : Optional[str] File token for accessing this file. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -726,13 +731,10 @@ def get_file_preview( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if width is not None: api_params['width'] = self._normalize_value(width) if height is not None: @@ -758,19 +760,23 @@ def get_file_preview( if token is not None: api_params['token'] = self._normalize_value(token) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'image/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'image/*', + }, + api_params, + ) return response - def get_file_view( self, bucket_id: str, file_id: str, - token: Optional[str] = None + token: Optional[str] = None, ) -> bytes: """ Get a file content by its unique ID. This endpoint is similar to the download method but returns with no 'Content-Disposition: attachment' header. @@ -783,12 +789,11 @@ def get_file_view( File ID. token : Optional[str] File token for accessing this file. - Returns ------- bytes Response as bytes - + Raises ------ AppwriteException @@ -799,20 +804,21 @@ def get_file_view( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if token is not None: api_params['token'] = self._normalize_value(token) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': '*/*', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': '*/*', + }, + api_params, + ) return response - diff --git a/appwrite/services/tables_db.py b/appwrite/services/tables_db.py index 94854111..808f9ad3 100644 --- a/appwrite/services/tables_db.py +++ b/appwrite/services/tables_db.py @@ -46,6 +46,7 @@ T = TypeVar('T') + class TablesDB(Service): def __init__(self, client) -> None: @@ -55,7 +56,7 @@ def list( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> DatabaseList: """ Get a list of all databases from the current Appwrite project. You can use the search parameter to filter your results. @@ -68,12 +69,11 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- DatabaseList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -82,7 +82,6 @@ def list( api_path = '/tablesdb' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -90,14 +89,18 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseList) - def create( self, database_id: str, @@ -105,11 +108,10 @@ def create( enabled: Optional[bool] = None, specification: Optional[str] = None, replicas: Optional[float] = None, - sync_mode: Optional[str] = None + sync_mode: Optional[str] = None, ) -> Database: """ Create a new Database. - Parameters ---------- @@ -125,12 +127,11 @@ def create( Number of high availability replicas (0-5) for the dedicated database backing this database. Requires a dedicated `specification`; must be 0 for a serverless database. High availability is enabled when greater than 0. sync_mode : Optional[str] Replication sync mode for the dedicated database backing this database. Requires a dedicated `specification`; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -141,11 +142,8 @@ def create( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['databaseId'] = self._normalize_value(database_id) api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -157,26 +155,29 @@ def create( if sync_mode is not None: api_params['syncMode'] = self._normalize_value(sync_mode) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - def list_specifications( - self + self, ) -> DedicatedDatabaseSpecificationList: """ List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. - Returns ------- DedicatedDatabaseSpecificationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -186,17 +187,21 @@ def list_specifications( api_path = '/tablesdb/specifications' api_params = {} - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DedicatedDatabaseSpecificationList) - def list_transactions( self, - queries: Optional[List[str]] = None + queries: Optional[List[str]] = None, ) -> TransactionList: """ List transactions across all databases. @@ -205,12 +210,11 @@ def list_transactions( ---------- queries : Optional[List[str]] Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). - Returns ------- TransactionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -219,21 +223,24 @@ def list_transactions( api_path = '/tablesdb/transactions' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TransactionList) - def create_transaction( self, - ttl: Optional[float] = None + ttl: Optional[float] = None, ) -> Transaction: """ Create a new transaction. @@ -242,12 +249,11 @@ def create_transaction( ---------- ttl : Optional[float] Seconds before the transaction expires. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -256,22 +262,25 @@ def create_transaction( api_path = '/tablesdb/transactions' api_params = {} - if ttl is not None: api_params['ttl'] = self._normalize_value(ttl) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - def get_transaction( self, - transaction_id: str + transaction_id: str, ) -> Transaction: """ Get a transaction by its unique ID. @@ -280,12 +289,11 @@ def get_transaction( ---------- transaction_id : str Transaction ID. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -296,23 +304,25 @@ def get_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - def update_transaction( self, transaction_id: str, commit: Optional[bool] = None, - rollback: Optional[bool] = None + rollback: Optional[bool] = None, ) -> Transaction: """ Update a transaction, to either commit or roll back its operations. @@ -325,12 +335,11 @@ def update_transaction( Commit transaction? rollback : Optional[bool] Rollback transaction? - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -341,26 +350,28 @@ def update_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - if commit is not None: api_params['commit'] = self._normalize_value(commit) if rollback is not None: api_params['rollback'] = self._normalize_value(rollback) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - def delete_transaction( self, - transaction_id: str + transaction_id: str, ) -> Dict[str, Any]: """ Delete a transaction by its unique ID. @@ -369,12 +380,11 @@ def delete_transaction( ---------- transaction_id : str Transaction ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -385,22 +395,24 @@ def delete_transaction( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_operations( self, transaction_id: str, - operations: Optional[List[Dict[str, Any]]] = None + operations: Optional[List[Dict[str, Any]]] = None, ) -> Transaction: """ Create multiple operations in a single transaction. @@ -411,12 +423,11 @@ def create_operations( Transaction ID. operations : Optional[List[Dict[str, Any]]] Array of staged operations. - Returns ------- Transaction API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -427,24 +438,26 @@ def create_operations( api_params = {} if transaction_id is None: raise AppwriteException('Missing required parameter: "transaction_id"') - api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) - if operations is not None: api_params['operations'] = self._normalize_value(operations) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Transaction) - def get( self, - database_id: str + database_id: str, ) -> Database: """ Get a database by its unique ID. This endpoint response returns a JSON object with the database metadata. @@ -453,12 +466,11 @@ def get( ---------- database_id : str Database ID. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -469,18 +481,20 @@ def get( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - def update( self, database_id: str, @@ -488,7 +502,7 @@ def update( enabled: Optional[bool] = None, specification: Optional[str] = None, replicas: Optional[float] = None, - sync_mode: Optional[str] = None + sync_mode: Optional[str] = None, ) -> Database: """ Update a database by its unique ID. @@ -507,12 +521,11 @@ def update( Number of high availability replicas (0-5) for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification. High availability is enabled when greater than 0. sync_mode : Optional[str] Replication sync mode for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. - Returns ------- Database API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -523,9 +536,7 @@ def update( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if enabled is not None: @@ -537,18 +548,22 @@ def update( if sync_mode is not None: api_params['syncMode'] = self._normalize_value(sync_mode) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Database) - def delete( self, - database_id: str + database_id: str, ) -> Dict[str, Any]: """ Delete a database by its unique ID. Only API keys with with databases.write scope can delete a database. @@ -557,12 +572,11 @@ def delete( ---------- database_id : str Database ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -573,25 +587,27 @@ def delete( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_failover( self, database_id: str, - target_replica_id: Optional[str] = None + target_replica_id: Optional[str] = None, ) -> DedicatedDatabase: """ - Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation by a failover that did not finish also accepts this call as a repair, provided `targetReplicaId` names the member to promote. + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. Parameters ---------- @@ -599,12 +615,11 @@ def create_failover( Database ID. target_replica_id : Optional[str] Target replica ID to promote. If not specified, the healthiest replica is selected. - Returns ------- DedicatedDatabase API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -615,24 +630,26 @@ def create_failover( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if target_replica_id is not None: api_params['targetReplicaId'] = self._normalize_value(target_replica_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DedicatedDatabase) - def list_migrations( self, - database_id: str + database_id: str, ) -> DatabaseMigrationList: """ List the dedicated migrations for a TablesDB database. A database has at most one in-flight migration. @@ -641,12 +658,11 @@ def list_migrations( ---------- database_id : str Database ID. - Returns ------- DatabaseMigrationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -657,23 +673,25 @@ def list_migrations( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseMigrationList) - def create_migration( self, database_id: str, specification: str, - auto_cutover: Optional[bool] = None + auto_cutover: Optional[bool] = None, ) -> DatabaseMigration: """ Start migrating a serverless TablesDB database onto a dedicated MySQL compute. Data is copied to the target while the source stays live, with a brief read-only window during cutover. @@ -686,12 +704,11 @@ def create_migration( Dedicated compute specification to provision as the migration target (e.g. s-2vcpu-4gb). The migration always targets a dedicated compute, so `serverless` is not accepted. auto_cutover : Optional[bool] Whether to cut over automatically once the copy is verified. When disabled the migration parks at ready_to_cutover and holds there until the cutover is performed manually. - Returns ------- DatabaseMigration API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -702,29 +719,30 @@ def create_migration( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if specification is None: raise AppwriteException('Missing required parameter: "specification"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - api_params['specification'] = self._normalize_value(specification) if auto_cutover is not None: api_params['autoCutover'] = self._normalize_value(auto_cutover) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseMigration) - def get_migration( self, database_id: str, - migration_id: str + migration_id: str, ) -> DatabaseMigration: """ Get a single dedicated migration for a TablesDB database by its ID. @@ -735,12 +753,11 @@ def get_migration( Database ID. migration_id : str Migration ID. - Returns ------- DatabaseMigration API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -751,26 +768,27 @@ def get_migration( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if migration_id is None: raise AppwriteException('Missing required parameter: "migration_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseMigration) - def delete_migration( self, database_id: str, - migration_id: str + migration_id: str, ) -> Dict[str, Any]: """ Abort an in-flight TablesDB dedicated migration. Only allowed before cutover; once the migration has cut over it cannot be aborted. @@ -781,12 +799,11 @@ def delete_migration( Database ID. migration_id : str Migration ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -797,27 +814,28 @@ def delete_migration( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if migration_id is None: raise AppwriteException('Missing required parameter: "migration_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def cutover_migration( self, database_id: str, - migration_id: str + migration_id: str, ) -> DatabaseMigration: """ Cut a verified TablesDB migration over to its dedicated compute. Only applies to a migration created with `autoCutover` disabled, which waits at `ready_to_cutover` until this is called. The routing flip happens shortly after this returns, with a brief read-only window. One call buys one attempt: a cutover that fails a check returns the migration to `verifying` and parks it again, so call this once more to retry. @@ -828,12 +846,11 @@ def cutover_migration( Database ID. migration_id : str Migration ID. - Returns ------- DatabaseMigration API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -844,29 +861,30 @@ def cutover_migration( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if migration_id is None: raise AppwriteException('Missing required parameter: "migration_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{migrationId}', str(self._normalize_value(migration_id))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseMigration) - def list_operations( self, database_id: str, status: Optional[str] = None, limit: Optional[float] = None, - offset: Optional[float] = None + offset: Optional[float] = None, ) -> DedicatedDatabaseOperationList: """ List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. @@ -881,12 +899,11 @@ def list_operations( Maximum number of operations to return. offset : Optional[float] Number of operations to skip. - Returns ------- DedicatedDatabaseOperationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -897,9 +914,7 @@ def list_operations( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if status is not None: api_params['status'] = self._normalize_value(status) if limit is not None: @@ -907,17 +922,21 @@ def list_operations( if offset is not None: api_params['offset'] = self._normalize_value(offset) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DedicatedDatabaseOperationList) - def get_replicas( self, - database_id: str + database_id: str, ) -> DedicatedDatabaseReplicas: """ Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. @@ -926,12 +945,11 @@ def get_replicas( ---------- database_id : str Database ID. - Returns ------- DedicatedDatabaseReplicas API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -942,21 +960,23 @@ def get_replicas( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DedicatedDatabaseReplicas) - def get_status( self, - database_id: str + database_id: str, ) -> DatabaseStatus: """ Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. @@ -965,12 +985,11 @@ def get_status( ---------- database_id : str Database ID. - Returns ------- DatabaseStatus API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -981,24 +1000,26 @@ def get_status( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=DatabaseStatus) - def list_tables( self, database_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> TableList: """ Get a list of all tables that belong to the provided databaseId. You can use the search parameter to filter your results. @@ -1013,12 +1034,11 @@ def list_tables( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- TableList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1029,9 +1049,7 @@ def list_tables( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -1039,14 +1057,18 @@ def list_tables( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TableList) - def create_table( self, database_id: str, @@ -1056,7 +1078,7 @@ def create_table( row_security: Optional[bool] = None, enabled: Optional[bool] = None, columns: Optional[List[Dict[str, Any]]] = None, - indexes: Optional[List[Dict[str, Any]]] = None + indexes: Optional[List[Dict[str, Any]]] = None, ) -> Table: """ Create a new Table. Before using this route, you should create a new database resource using either a [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable) API or directly from your database console. @@ -1079,12 +1101,11 @@ def create_table( Array of column definitions to create. Each column should contain: key (string), type (string: string, varchar, text, mediumtext, longtext, integer, bigint, double, boolean, datetime, point, linestring, polygon, email, url, ip, enum), size (integer, required for string and varchar types), required (boolean, optional), default (mixed, optional), array (boolean, optional), and type-specific options. indexes : Optional[List[Dict[str, Any]]] Array of index definitions to create. Each index should contain: key (string), type (string: key, fulltext, unique, spatial), attributes (array of column keys), orders (array of ASC/DESC, optional), and lengths (array of integers, optional). - Returns ------- Table API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1095,15 +1116,11 @@ def create_table( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) - api_params['tableId'] = self._normalize_value(table_id) api_params['name'] = self._normalize_value(name) if permissions is not None: @@ -1117,19 +1134,23 @@ def create_table( if indexes is not None: api_params['indexes'] = self._normalize_value(indexes) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Table) - def get_table( self, database_id: str, - table_id: str + table_id: str, ) -> Table: """ Get a table by its unique ID. This endpoint response returns a JSON object with the table metadata. @@ -1140,12 +1161,11 @@ def get_table( Database ID. table_id : str Table ID. - Returns ------- Table API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1156,22 +1176,23 @@ def get_table( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Table) - def update_table( self, database_id: str, @@ -1180,7 +1201,7 @@ def update_table( permissions: Optional[List[str]] = None, row_security: Optional[bool] = None, enabled: Optional[bool] = None, - purge: Optional[bool] = None + purge: Optional[bool] = None, ) -> Table: """ Update a table by its unique ID. @@ -1201,12 +1222,11 @@ def update_table( Is table enabled? When set to 'disabled', users cannot access the table but Server SDKs with and API key can still read and write to the table. No data is lost when this is toggled. purge : Optional[bool] When true, purge all cached list responses for this table as part of the update. Use this to force readers to see fresh data immediately instead of waiting for the cache TTL to expire. - Returns ------- Table API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1217,13 +1237,10 @@ def update_table( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if name is not None: api_params['name'] = self._normalize_value(name) if permissions is not None: @@ -1235,19 +1252,23 @@ def update_table( if purge is not None: api_params['purge'] = self._normalize_value(purge) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Table) - def delete_table( self, database_id: str, - table_id: str + table_id: str, ) -> Dict[str, Any]: """ Delete a table by its unique ID. Only users with write permissions have access to delete this resource. @@ -1258,12 +1279,11 @@ def delete_table( Database ID. table_id : str Table ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1274,28 +1294,29 @@ def delete_table( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_columns( self, database_id: str, table_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ColumnList: """ List columns in the table. @@ -1310,12 +1331,11 @@ def list_columns( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following columns: key, type, size, required, array, status, error total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ColumnList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1326,26 +1346,27 @@ def list_columns( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnList) - def create_big_int_column( self, database_id: str, @@ -1355,11 +1376,10 @@ def create_big_int_column( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnBigint: """ Create a bigint column. Optionally, minimum and maximum values can be provided. - Parameters ---------- @@ -1379,12 +1399,11 @@ def create_big_int_column( Default value. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnBigint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1395,19 +1414,14 @@ def create_big_int_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -1419,15 +1433,19 @@ def create_big_int_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnBigint) - def update_big_int_column( self, database_id: str, @@ -1437,11 +1455,10 @@ def update_big_int_column( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnBigint: """ Update a bigint column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -1461,12 +1478,11 @@ def update_big_int_column( Maximum value new_key : Optional[str] New Column Key. - Returns ------- ColumnBigint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1477,20 +1493,15 @@ def update_big_int_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -1500,15 +1511,19 @@ def update_big_int_column( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnBigint) - def create_boolean_column( self, database_id: str, @@ -1516,11 +1531,10 @@ def create_boolean_column( key: str, required: bool, default: Optional[bool] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnBoolean: """ Create a boolean column. - Parameters ---------- @@ -1536,12 +1550,11 @@ def create_boolean_column( Default value for column when not provided. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnBoolean API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1552,19 +1565,14 @@ def create_boolean_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1572,15 +1580,19 @@ def create_boolean_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnBoolean) - def update_boolean_column( self, database_id: str, @@ -1588,7 +1600,7 @@ def update_boolean_column( key: str, required: bool, default: Optional[bool], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnBoolean: """ Update a boolean column. Changing the `default` value will not update already existing rows. @@ -1607,12 +1619,11 @@ def update_boolean_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnBoolean API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1623,34 +1634,33 @@ def update_boolean_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnBoolean) - def create_datetime_column( self, database_id: str, @@ -1658,7 +1668,7 @@ def create_datetime_column( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnDatetime: """ Create a date time column according to the ISO 8601 standard. @@ -1677,12 +1687,11 @@ def create_datetime_column( Default value for the column in [ISO 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnDatetime API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1693,19 +1702,14 @@ def create_datetime_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1713,15 +1717,19 @@ def create_datetime_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnDatetime) - def update_datetime_column( self, database_id: str, @@ -1729,7 +1737,7 @@ def update_datetime_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnDatetime: """ Update a date time column. Changing the `default` value will not update already existing rows. @@ -1748,12 +1756,11 @@ def update_datetime_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnDatetime API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1764,34 +1771,33 @@ def update_datetime_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnDatetime) - def create_email_column( self, database_id: str, @@ -1799,11 +1805,10 @@ def create_email_column( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnEmail: """ Create an email column. - Parameters ---------- @@ -1819,12 +1824,11 @@ def create_email_column( Default value for column when not provided. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnEmail API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1835,19 +1839,14 @@ def create_email_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -1855,15 +1854,19 @@ def create_email_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnEmail) - def update_email_column( self, database_id: str, @@ -1871,11 +1874,10 @@ def update_email_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnEmail: """ Update an email column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -1891,12 +1893,11 @@ def update_email_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnEmail API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1907,34 +1908,33 @@ def update_email_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnEmail) - def create_enum_column( self, database_id: str, @@ -1943,7 +1943,7 @@ def create_enum_column( elements: List[str], required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnEnum: """ Create an enumeration column. The `elements` param acts as a white-list of accepted values for this column. @@ -1964,12 +1964,11 @@ def create_enum_column( Default value for column when not provided. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnEnum API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1980,22 +1979,16 @@ def create_enum_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if elements is None: raise AppwriteException('Missing required parameter: "elements"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) @@ -2004,15 +1997,19 @@ def create_enum_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnEnum) - def update_enum_column( self, database_id: str, @@ -2021,11 +2018,10 @@ def update_enum_column( elements: List[str], required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnEnum: """ Update an enum column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2043,12 +2039,11 @@ def update_enum_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnEnum API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2059,38 +2054,36 @@ def update_enum_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if elements is None: raise AppwriteException('Missing required parameter: "elements"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['elements'] = self._normalize_value(elements) api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnEnum) - def create_float_column( self, database_id: str, @@ -2100,11 +2093,10 @@ def create_float_column( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnFloat: """ Create a float column. Optionally, minimum and maximum values can be provided. - Parameters ---------- @@ -2124,12 +2116,11 @@ def create_float_column( Default value. Cannot be set when required. array : Optional[bool] Is column an array? - Returns ------- ColumnFloat API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2140,19 +2131,14 @@ def create_float_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -2164,15 +2150,19 @@ def create_float_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnFloat) - def update_float_column( self, database_id: str, @@ -2182,11 +2172,10 @@ def update_float_column( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnFloat: """ Update a float column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2206,12 +2195,11 @@ def update_float_column( Maximum value new_key : Optional[str] New Column Key. - Returns ------- ColumnFloat API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2222,20 +2210,15 @@ def update_float_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -2245,15 +2228,19 @@ def update_float_column( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnFloat) - def create_integer_column( self, database_id: str, @@ -2263,11 +2250,10 @@ def create_integer_column( min: Optional[float] = None, max: Optional[float] = None, default: Optional[float] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnInteger: """ Create an integer column. Optionally, minimum and maximum values can be provided. - Parameters ---------- @@ -2287,12 +2273,11 @@ def create_integer_column( Default value. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnInteger API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2303,19 +2288,14 @@ def create_integer_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if min is not None: @@ -2327,15 +2307,19 @@ def create_integer_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnInteger) - def update_integer_column( self, database_id: str, @@ -2345,11 +2329,10 @@ def update_integer_column( default: Optional[float], min: Optional[float] = None, max: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnInteger: """ Update an integer column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2369,12 +2352,11 @@ def update_integer_column( Maximum value new_key : Optional[str] New Column Key. - Returns ------- ColumnInteger API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2385,20 +2367,15 @@ def update_integer_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if min is not None: api_params['min'] = self._normalize_value(min) @@ -2408,15 +2385,19 @@ def update_integer_column( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnInteger) - def create_ip_column( self, database_id: str, @@ -2424,11 +2405,10 @@ def create_ip_column( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnIp: """ Create IP address column. - Parameters ---------- @@ -2444,12 +2424,11 @@ def create_ip_column( Default value. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnIp API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2460,19 +2439,14 @@ def create_ip_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2480,15 +2454,19 @@ def create_ip_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnIp) - def update_ip_column( self, database_id: str, @@ -2496,11 +2474,10 @@ def update_ip_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnIp: """ Update an ip column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2516,12 +2493,11 @@ def update_ip_column( Default value. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnIp API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2532,41 +2508,40 @@ def update_ip_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnIp) - def create_line_column( self, database_id: str, table_id: str, key: str, required: bool, - default: Optional[List[List[Any]]] = None + default: Optional[List[List[Any]]] = None, ) -> ColumnLine: """ Create a geometric line column. @@ -2583,12 +2558,11 @@ def create_line_column( Is column required? default : Optional[List[List[Any]]] Default value for column when not provided, two-dimensional array of coordinate pairs, [[longitude, latitude], [longitude, latitude], …], listing the vertices of the line in order. Cannot be set when column is required. - Returns ------- ColumnLine API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2599,33 +2573,32 @@ def create_line_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnLine) - def update_line_column( self, database_id: str, @@ -2633,7 +2606,7 @@ def update_line_column( key: str, required: bool, default: Optional[List[List[Any]]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnLine: """ Update a line column. Changing the `default` value will not update already existing rows. @@ -2652,12 +2625,11 @@ def update_line_column( Default value for column when not provided, two-dimensional array of coordinate pairs, [[longitude, latitude], [longitude, latitude], …], listing the vertices of the line in order. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnLine API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2668,35 +2640,34 @@ def update_line_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnLine) - def create_longtext_column( self, database_id: str, @@ -2705,11 +2676,10 @@ def create_longtext_column( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> ColumnLongtext: """ Create a longtext column. - Parameters ---------- @@ -2727,12 +2697,11 @@ def create_longtext_column( Is column an array? encrypt : Optional[bool] Toggle encryption for the column. Encryption enhances security by not storing any plain text values in the database. However, encrypted columns cannot be queried. - Returns ------- ColumnLongtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2743,19 +2712,14 @@ def create_longtext_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2765,15 +2729,19 @@ def create_longtext_column( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnLongtext) - def update_longtext_column( self, database_id: str, @@ -2781,11 +2749,10 @@ def update_longtext_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnLongtext: """ Update a longtext column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2801,12 +2768,11 @@ def update_longtext_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnLongtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2817,34 +2783,33 @@ def update_longtext_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnLongtext) - def create_mediumtext_column( self, database_id: str, @@ -2853,11 +2818,10 @@ def create_mediumtext_column( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> ColumnMediumtext: """ Create a mediumtext column. - Parameters ---------- @@ -2875,12 +2839,11 @@ def create_mediumtext_column( Is column an array? encrypt : Optional[bool] Toggle encryption for the column. Encryption enhances security by not storing any plain text values in the database. However, encrypted columns cannot be queried. - Returns ------- ColumnMediumtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2891,19 +2854,14 @@ def create_mediumtext_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -2913,15 +2871,19 @@ def create_mediumtext_column( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnMediumtext) - def update_mediumtext_column( self, database_id: str, @@ -2929,11 +2891,10 @@ def update_mediumtext_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnMediumtext: """ Update a mediumtext column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -2949,12 +2910,11 @@ def update_mediumtext_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnMediumtext API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2965,41 +2925,40 @@ def update_mediumtext_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnMediumtext) - def create_point_column( self, database_id: str, table_id: str, key: str, required: bool, - default: Optional[List[float]] = None + default: Optional[List[float]] = None, ) -> ColumnPoint: """ Create a geometric point column. @@ -3016,12 +2975,11 @@ def create_point_column( Is column required? default : Optional[List[float]] Default value for column when not provided, array of two numbers [longitude, latitude], representing a single coordinate. Cannot be set when column is required. - Returns ------- ColumnPoint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3032,33 +2990,32 @@ def create_point_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnPoint) - def update_point_column( self, database_id: str, @@ -3066,7 +3023,7 @@ def update_point_column( key: str, required: bool, default: Optional[List[float]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnPoint: """ Update a point column. Changing the `default` value will not update already existing rows. @@ -3085,12 +3042,11 @@ def update_point_column( Default value for column when not provided, array of two numbers [longitude, latitude], representing a single coordinate. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnPoint API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3101,42 +3057,41 @@ def update_point_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnPoint) - def create_polygon_column( self, database_id: str, table_id: str, key: str, required: bool, - default: Optional[List[List[Any]]] = None + default: Optional[List[List[Any]]] = None, ) -> ColumnPolygon: """ Create a geometric polygon column. @@ -3153,12 +3108,11 @@ def create_polygon_column( Is column required? default : Optional[List[List[Any]]] Default value for column when not provided, three-dimensional array where the outer array holds one or more linear rings, [[[longitude, latitude], …], …], the first ring is the exterior boundary, any additional rings are interior holes, and each ring must start and end with the same coordinate pair. Cannot be set when column is required. - Returns ------- ColumnPolygon API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3169,33 +3123,32 @@ def create_polygon_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnPolygon) - def update_polygon_column( self, database_id: str, @@ -3203,7 +3156,7 @@ def update_polygon_column( key: str, required: bool, default: Optional[List[List[Any]]] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnPolygon: """ Update a polygon column. Changing the `default` value will not update already existing rows. @@ -3222,12 +3175,11 @@ def update_polygon_column( Default value for column when not provided, three-dimensional array where the outer array holds one or more linear rings, [[[longitude, latitude], …], …], the first ring is the exterior boundary, any additional rings are interior holes, and each ring must start and end with the same coordinate pair. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnPolygon API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3238,35 +3190,34 @@ def update_polygon_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) if default is not None: api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnPolygon) - def create_relationship_column( self, database_id: str, @@ -3276,11 +3227,10 @@ def create_relationship_column( two_way: Optional[bool] = None, key: Optional[str] = None, two_way_key: Optional[str] = None, - on_delete: Optional[RelationMutate] = None + on_delete: Optional[RelationMutate] = None, ) -> ColumnRelationship: """ Create relationship column. [Learn more about relationship columns](https://appwrite.io/docs/databases-relationships#relationship-columns). - Parameters ---------- @@ -3300,12 +3250,11 @@ def create_relationship_column( Two Way Column Key. on_delete : Optional[RelationMutate] Delete constraint. Possible values are: cascade, restrict, setNull. - Returns ------- ColumnRelationship API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3316,19 +3265,14 @@ def create_relationship_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if related_table_id is None: raise AppwriteException('Missing required parameter: "related_table_id"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['relatedTableId'] = self._normalize_value(related_table_id) api_params['type'] = self._normalize_value(type) if two_way is not None: @@ -3340,15 +3284,19 @@ def create_relationship_column( if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnRelationship) - @deprecated("This API has been deprecated since 1.9.0. Please use `tablesDB.create_text_column` instead.") def create_string_column( self, @@ -3359,11 +3307,10 @@ def create_string_column( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> ColumnString: """ Create a string column. - .. deprecated::1.9.0 This API has been deprecated since 1.9.0. Please use `tablesDB.create_text_column` instead. @@ -3385,12 +3332,11 @@ def create_string_column( Is column an array? encrypt : Optional[bool] Toggle encryption for the column. Encryption enhances security by not storing any plain text values in the database. However, encrypted columns cannot be queried. - Returns ------- ColumnString API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3401,22 +3347,16 @@ def create_string_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if size is None: raise AppwriteException('Missing required parameter: "size"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) @@ -3427,15 +3367,19 @@ def create_string_column( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnString) - @deprecated("This API has been deprecated since 1.8.0. Please use `tablesDB.update_text_column` instead.") def update_string_column( self, @@ -3445,11 +3389,10 @@ def update_string_column( required: bool, default: Optional[str], size: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnString: """ Update a string column. Changing the `default` value will not update already existing rows. - .. deprecated::1.8.0 This API has been deprecated since 1.8.0. Please use `tablesDB.update_text_column` instead. @@ -3469,12 +3412,11 @@ def update_string_column( Maximum size of the string column. new_key : Optional[str] New Column Key. - Returns ------- ColumnString API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3485,20 +3427,15 @@ def update_string_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if size is not None: @@ -3506,15 +3443,19 @@ def update_string_column( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnString) - def create_text_column( self, database_id: str, @@ -3523,11 +3464,10 @@ def create_text_column( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> ColumnText: """ Create a text column. - Parameters ---------- @@ -3545,12 +3485,11 @@ def create_text_column( Is column an array? encrypt : Optional[bool] Toggle encryption for the column. Encryption enhances security by not storing any plain text values in the database. However, encrypted columns cannot be queried. - Returns ------- ColumnText API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3561,19 +3500,14 @@ def create_text_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -3583,15 +3517,19 @@ def create_text_column( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnText) - def update_text_column( self, database_id: str, @@ -3599,11 +3537,10 @@ def update_text_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnText: """ Update a text column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -3619,12 +3556,11 @@ def update_text_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnText API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3635,34 +3571,33 @@ def update_text_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnText) - def create_url_column( self, database_id: str, @@ -3670,11 +3605,10 @@ def create_url_column( key: str, required: bool, default: Optional[str] = None, - array: Optional[bool] = None + array: Optional[bool] = None, ) -> ColumnUrl: """ Create a URL column. - Parameters ---------- @@ -3690,12 +3624,11 @@ def create_url_column( Default value for column when not provided. Cannot be set when column is required. array : Optional[bool] Is column an array? - Returns ------- ColumnUrl API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3706,19 +3639,14 @@ def create_url_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['required'] = self._normalize_value(required) if default is not None: @@ -3726,15 +3654,19 @@ def create_url_column( if array is not None: api_params['array'] = self._normalize_value(array) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnUrl) - def update_url_column( self, database_id: str, @@ -3742,11 +3674,10 @@ def update_url_column( key: str, required: bool, default: Optional[str], - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnUrl: """ Update an url column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -3762,12 +3693,11 @@ def update_url_column( Default value for column when not provided. Cannot be set when column is required. new_key : Optional[str] New Column Key. - Returns ------- ColumnUrl API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3778,34 +3708,33 @@ def update_url_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnUrl) - def create_varchar_column( self, database_id: str, @@ -3815,11 +3744,10 @@ def create_varchar_column( required: bool, default: Optional[str] = None, array: Optional[bool] = None, - encrypt: Optional[bool] = None + encrypt: Optional[bool] = None, ) -> ColumnVarchar: """ Create a varchar column. - Parameters ---------- @@ -3839,12 +3767,11 @@ def create_varchar_column( Is column an array? encrypt : Optional[bool] Toggle encryption for the column. Encryption enhances security by not storing any plain text values in the database. However, encrypted columns cannot be queried. - Returns ------- ColumnVarchar API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3855,22 +3782,16 @@ def create_varchar_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if size is None: raise AppwriteException('Missing required parameter: "size"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['size'] = self._normalize_value(size) api_params['required'] = self._normalize_value(required) @@ -3881,15 +3802,19 @@ def create_varchar_column( if encrypt is not None: api_params['encrypt'] = self._normalize_value(encrypt) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnVarchar) - def update_varchar_column( self, database_id: str, @@ -3898,11 +3823,10 @@ def update_varchar_column( required: bool, default: Optional[str], size: Optional[float] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnVarchar: """ Update a varchar column. Changing the `default` value will not update already existing rows. - Parameters ---------- @@ -3920,12 +3844,11 @@ def update_varchar_column( Maximum size of the varchar column. new_key : Optional[str] New Column Key. - Returns ------- ColumnVarchar API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -3936,20 +3859,15 @@ def update_varchar_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if required is None: raise AppwriteException('Missing required parameter: "required"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - api_params['required'] = self._normalize_value(required) api_params['default'] = self._normalize_value(default) if size is not None: @@ -3957,21 +3875,36 @@ def update_varchar_column( if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnVarchar) - def get_column( self, database_id: str, table_id: str, - key: str - ) -> Union[ColumnBoolean, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnString]: + key: str, + ) -> Union[ + ColumnBoolean, + ColumnInteger, + ColumnFloat, + ColumnEmail, + ColumnEnum, + ColumnUrl, + ColumnIp, + ColumnDatetime, + ColumnRelationship, + ColumnString, + ]: """ Get column by ID. @@ -3983,12 +3916,11 @@ def get_column( Table ID. key : str Column Key. - Returns ------- Union[ColumnBoolean, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnString] API response as one of the typed response models - + Raises ------ AppwriteException @@ -3999,22 +3931,23 @@ def get_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) if not isinstance(response, dict): raise AppwriteException('Expected object response when hydrating a response model') @@ -4050,12 +3983,11 @@ def get_column( raise AppwriteException('Unable to match response to any known model') - def delete_column( self, database_id: str, table_id: str, - key: str + key: str, ) -> Dict[str, Any]: """ Deletes a column. @@ -4068,12 +4000,11 @@ def delete_column( Table ID. key : str Column Key. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -4084,37 +4015,36 @@ def delete_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_relationship_column( self, database_id: str, table_id: str, key: str, on_delete: Optional[RelationMutate] = None, - new_key: Optional[str] = None + new_key: Optional[str] = None, ) -> ColumnRelationship: """ Update relationship column. [Learn more about relationship columns](https://appwrite.io/docs/databases-relationships#relationship-columns). - Parameters ---------- @@ -4128,12 +4058,11 @@ def update_relationship_column( Delete constraint. Possible values are: cascade, restrict, setNull. new_key : Optional[str] New Column Key. - Returns ------- ColumnRelationship API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4144,37 +4073,37 @@ def update_relationship_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - if on_delete is not None: api_params['onDelete'] = self._normalize_value(on_delete) if new_key is not None: api_params['newKey'] = self._normalize_value(new_key) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnRelationship) - def list_indexes( self, database_id: str, table_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ColumnIndexList: """ List indexes on the table. @@ -4189,12 +4118,11 @@ def list_indexes( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following columns: key, type, status, attributes, error total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ColumnIndexList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4205,26 +4133,27 @@ def list_indexes( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnIndexList) - def create_index( self, database_id: str, @@ -4233,7 +4162,7 @@ def create_index( type: TablesDBIndexType, columns: List[str], orders: Optional[List[OrderBy]] = None, - lengths: Optional[List[float]] = None + lengths: Optional[List[float]] = None, ) -> ColumnIndex: """ Creates an index on the columns listed. Your index should include all the columns you will query in a single request. @@ -4255,12 +4184,11 @@ def create_index( Array of index orders. Maximum of 100 orders are allowed. lengths : Optional[List[float]] Length of index. Maximum of 100 - Returns ------- ColumnIndex API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4271,22 +4199,16 @@ def create_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - if columns is None: raise AppwriteException('Missing required parameter: "columns"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['key'] = self._normalize_value(key) api_params['type'] = self._normalize_value(type) api_params['columns'] = self._normalize_value(columns) @@ -4295,20 +4217,24 @@ def create_index( if lengths is not None: api_params['lengths'] = self._normalize_value(lengths) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnIndex) - def get_index( self, database_id: str, table_id: str, - key: str + key: str, ) -> ColumnIndex: """ Get index by ID. @@ -4321,12 +4247,11 @@ def get_index( Table ID. You can create a new table using the Database service [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable). key : str Index Key. - Returns ------- ColumnIndex API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4337,31 +4262,31 @@ def get_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ColumnIndex) - def delete_index( self, database_id: str, table_id: str, - key: str + key: str, ) -> Dict[str, Any]: """ Delete an index. @@ -4374,12 +4299,11 @@ def delete_index( Table ID. You can create a new table using the TablesDB service [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable). key : str Index Key. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -4390,26 +4314,26 @@ def delete_index( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if key is None: raise AppwriteException('Missing required parameter: "key"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{key}', str(self._normalize_value(key))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_rows( self, database_id: str, @@ -4418,7 +4342,7 @@ def list_rows( transaction_id: Optional[str] = None, total: Optional[bool] = None, ttl: Optional[float] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> RowList[T]: """ Get a list of all the user's rows in a given table. You can use the query params to filter your results. @@ -4437,15 +4361,14 @@ def list_rows( When set to false, the total count returned will be 0 and will not be calculated. ttl : Optional[float] TTL (seconds) for caching list responses. Responses are stored in an in-memory key-value cache, keyed per project, table, schema version (columns and indexes), caller authorization roles, and the exact query — so users with different permissions never share cached entries. Schema changes invalidate cached entries automatically; row writes do not, so choose a TTL you are comfortable serving as stale data. Set to 0 to disable caching. Must be between 0 and 86400 (24 hours). - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- RowList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4456,13 +4379,10 @@ def list_rows( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: @@ -4472,14 +4392,18 @@ def list_rows( if ttl is not None: api_params['ttl'] = self._normalize_value(ttl) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return RowList.with_data(response, model_type) - def create_row( self, database_id: str, @@ -4488,7 +4412,7 @@ def create_row( data: Dict[str, Any], permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Create a new Row. Before using this route, you should create a new table resource using either a [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable) API or directly from your database console. @@ -4507,15 +4431,14 @@ def create_row( An array of permissions strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4526,19 +4449,14 @@ def create_row( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - if data is None: raise AppwriteException('Missing required parameter: "data"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['rowId'] = self._normalize_value(row_id) api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -4546,22 +4464,26 @@ def create_row( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - def create_rows( self, database_id: str, table_id: str, rows: List[Dict[str, Any]], transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> RowList[T]: """ Create new Rows. Before using this route, you should create a new table resource using either a [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable) API or directly from your database console. @@ -4576,15 +4498,14 @@ def create_rows( Array of rows data as JSON objects. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- RowList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4595,40 +4516,39 @@ def create_rows( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if rows is None: raise AppwriteException('Missing required parameter: "rows"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['rows'] = self._normalize_value(rows) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return RowList.with_data(response, model_type) - def upsert_rows( self, database_id: str, table_id: str, rows: List[Dict[str, Any]], transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> RowList[T]: """ Create or update Rows. Before using this route, you should create a new table resource using either a [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable) API or directly from your database console. - Parameters ---------- @@ -4640,15 +4560,14 @@ def upsert_rows( Array of row data as JSON objects. May contain partial rows. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- RowList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4659,29 +4578,29 @@ def upsert_rows( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if rows is None: raise AppwriteException('Missing required parameter: "rows"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - api_params['rows'] = self._normalize_value(rows) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return RowList.with_data(response, model_type) - def update_rows( self, database_id: str, @@ -4689,7 +4608,7 @@ def update_rows( data: Optional[Dict[str, Any]] = None, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> RowList[T]: """ Update all rows that match your queries, if no queries are submitted then all rows are updated. You can pass only specific fields to be updated. @@ -4706,15 +4625,14 @@ def update_rows( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- RowList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4725,13 +4643,10 @@ def update_rows( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if queries is not None: @@ -4739,22 +4654,26 @@ def update_rows( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return RowList.with_data(response, model_type) - def delete_rows( self, database_id: str, table_id: str, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> RowList[T]: """ Bulk delete rows using queries, if no queries are passed then all rows are deleted. @@ -4769,15 +4688,14 @@ def delete_rows( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- RowList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4788,27 +4706,28 @@ def delete_rows( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return RowList.with_data(response, model_type) - def get_row( self, database_id: str, @@ -4816,7 +4735,7 @@ def get_row( row_id: str, queries: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Get a row by its unique ID. This endpoint response returns a JSON object with the row data. @@ -4833,15 +4752,14 @@ def get_row( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. transaction_id : Optional[str] Transaction ID to read uncommitted changes within the transaction. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4852,30 +4770,30 @@ def get_row( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - def upsert_row( self, database_id: str, @@ -4884,7 +4802,7 @@ def upsert_row( data: Optional[Dict[str, Any]] = None, permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Create or update a Row. Before using this route, you should create a new table resource using either a [server integration](https://appwrite.io/docs/references/cloud/server-dart/tablesDB#createTable) API or directly from your database console. @@ -4903,15 +4821,14 @@ def upsert_row( An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4922,17 +4839,13 @@ def upsert_row( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -4940,15 +4853,19 @@ def upsert_row( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - def update_row( self, database_id: str, @@ -4957,7 +4874,7 @@ def update_row( data: Optional[Dict[str, Any]] = None, permissions: Optional[List[str]] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Update a row by its unique ID. Using the patch method you can pass only specific fields that will get updated. @@ -4976,15 +4893,14 @@ def update_row( An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -4995,17 +4911,13 @@ def update_row( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) - if data is not None: api_params['data'] = self._normalize_value(data) if permissions is not None: @@ -5013,21 +4925,25 @@ def update_row( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - def delete_row( self, database_id: str, table_id: str, row_id: str, - transaction_id: Optional[str] = None + transaction_id: Optional[str] = None, ) -> Dict[str, Any]: """ Delete a row by its unique ID. @@ -5042,12 +4958,11 @@ def delete_row( Row ID. transaction_id : Optional[str] Transaction ID for staging the operation. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -5058,28 +4973,28 @@ def delete_row( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) - if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def decrement_row_column( self, database_id: str, @@ -5089,7 +5004,7 @@ def decrement_row_column( value: Optional[float] = None, min: Optional[float] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Decrement a specific column of a row by a given value. @@ -5110,15 +5025,14 @@ def decrement_row_column( Minimum value for the column. If the current value is lesser than this value, an exception will be thrown. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5129,21 +5043,16 @@ def decrement_row_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - if column is None: raise AppwriteException('Missing required parameter: "column"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) api_path = api_path.replace('{column}', str(self._normalize_value(column))) - if value is not None: api_params['value'] = self._normalize_value(value) if min is not None: @@ -5151,15 +5060,19 @@ def decrement_row_column( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - def increment_row_column( self, database_id: str, @@ -5169,7 +5082,7 @@ def increment_row_column( value: Optional[float] = None, max: Optional[float] = None, transaction_id: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Row[T]: """ Increment a specific column of a row by a given value. @@ -5190,15 +5103,14 @@ def increment_row_column( Maximum value for the column. If the current value is greater than this value, an error will be thrown. transaction_id : Optional[str] Transaction ID for staging the operation. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Row[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -5209,21 +5121,16 @@ def increment_row_column( api_params = {} if database_id is None: raise AppwriteException('Missing required parameter: "database_id"') - if table_id is None: raise AppwriteException('Missing required parameter: "table_id"') - if row_id is None: raise AppwriteException('Missing required parameter: "row_id"') - if column is None: raise AppwriteException('Missing required parameter: "column"') - api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) api_path = api_path.replace('{tableId}', str(self._normalize_value(table_id))) api_path = api_path.replace('{rowId}', str(self._normalize_value(row_id))) api_path = api_path.replace('{column}', str(self._normalize_value(column))) - if value is not None: api_params['value'] = self._normalize_value(value) if max is not None: @@ -5231,11 +5138,15 @@ def increment_row_column( if transaction_id is not None: api_params['transactionId'] = self._normalize_value(transaction_id) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Row.with_data(response, model_type) - diff --git a/appwrite/services/teams.py b/appwrite/services/teams.py index 45594204..9df2eb7e 100644 --- a/appwrite/services/teams.py +++ b/appwrite/services/teams.py @@ -13,6 +13,7 @@ T = TypeVar('T') + class Teams(Service): def __init__(self, client) -> None: @@ -23,7 +24,7 @@ def list( queries: Optional[List[str]] = None, search: Optional[str] = None, total: Optional[bool] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> TeamList[T]: """ Get a list of all the teams in which the current user is a member. You can use the parameters to filter your results. @@ -36,15 +37,14 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- TeamList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -53,7 +53,6 @@ def list( api_path = '/teams' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -61,20 +60,24 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return TeamList.with_data(response, model_type) - def create( self, team_id: str, name: str, roles: Optional[List[str]] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Team[T]: """ Create a new team. The user who creates the team will automatically be assigned as the owner of the team. Only the users with the owner role can invite new members, add new owners and delete or update the team. @@ -87,15 +90,14 @@ def create( Team name. Max length: 128 chars. roles : Optional[List[str]] Array of strings. Use this param to set the roles in the team for the user who created it. The default role is **owner**. A role can be any string. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). Maximum of 100 roles are allowed, each 32 characters long. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Team[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -106,29 +108,30 @@ def create( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - - api_params['teamId'] = self._normalize_value(team_id) api_params['name'] = self._normalize_value(name) if roles is not None: api_params['roles'] = self._normalize_value(roles) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Team.with_data(response, model_type) - def get( self, team_id: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Team[T]: """ Get a team by its ID. All team members have read access for this resource. @@ -137,15 +140,14 @@ def get( ---------- team_id : str Team ID. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Team[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -156,23 +158,25 @@ def get( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Team.with_data(response, model_type) - def update_name( self, team_id: str, name: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Team[T]: """ Update the team's name by its unique ID. @@ -183,15 +187,14 @@ def update_name( Team ID. name : str New team name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Team[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -202,26 +205,27 @@ def update_name( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - api_params['name'] = self._normalize_value(name) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Team.with_data(response, model_type) - def delete( self, - team_id: str + team_id: str, ) -> Dict[str, Any]: """ Delete a team using its ID. Only team members with the owner role can delete the team. @@ -230,12 +234,11 @@ def delete( ---------- team_id : str Team ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -246,23 +249,25 @@ def delete( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def list_installations( self, team_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> AppInstallationList: """ List app installations on a team. Any team member can read installations. @@ -275,12 +280,11 @@ def list_installations( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- AppInstallationList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -291,27 +295,29 @@ def list_installations( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallationList) - def create_installation( self, team_id: str, app_id: str, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, ) -> AppInstallation: """ Install an app on a team. When authenticated as a user, only team members with the owner role can install apps. Requests using an API key or in admin mode can install apps on any team. The installation is granted the scopes the app currently requests. @@ -324,12 +330,11 @@ def create_installation( Application unique ID. authorization_details : Optional[str] Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. The Appwrite Console stores authorized project IDs here. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -340,29 +345,30 @@ def create_installation( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if app_id is None: raise AppwriteException('Missing required parameter: "app_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - api_params['appId'] = self._normalize_value(app_id) if authorization_details is not None: api_params['authorizationDetails'] = self._normalize_value(authorization_details) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def get_installation( self, team_id: str, - installation_id: str + installation_id: str, ) -> AppInstallation: """ Get an app installation on a team by its unique ID. Any team member can read installations. @@ -373,12 +379,11 @@ def get_installation( Team ID. installation_id : str Installation unique ID. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -389,27 +394,28 @@ def get_installation( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def update_installation( self, team_id: str, installation_id: str, - authorization_details: Optional[str] = None + authorization_details: Optional[str] = None, ) -> AppInstallation: """ Update an app installation on a team. Only team members with the owner role can update installations. The installation's granted scopes are refreshed to the scopes the app currently requests; previously issued installation access tokens are revoked. @@ -422,12 +428,11 @@ def update_installation( Installation unique ID. authorization_details : Optional[str] Authorization details granted to the installation as a JSON array of objects, each with a `type` and app-defined fields. Omit to keep the current value. - Returns ------- AppInstallation API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -438,29 +443,30 @@ def update_installation( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - if authorization_details is not None: api_params['authorizationDetails'] = self._normalize_value(authorization_details) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=AppInstallation) - def delete_installation( self, team_id: str, - installation_id: str + installation_id: str, ) -> Dict[str, Any]: """ Uninstall an app from a team by its installation ID. Only team members with the owner role can remove installations. Previously issued installation access tokens are revoked. @@ -471,12 +477,11 @@ def delete_installation( Team ID. installation_id : str Installation unique ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -487,29 +492,30 @@ def delete_installation( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if installation_id is None: raise AppwriteException('Missing required parameter: "installation_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{installationId}', str(self._normalize_value(installation_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return response - def list_memberships( self, team_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> MembershipList: """ Use this endpoint to list a team's members using the team's ID. All team members have read access to this endpoint. Hide sensitive attributes from the response by toggling membership privacy in the Console. @@ -524,12 +530,11 @@ def list_memberships( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- MembershipList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -540,9 +545,7 @@ def list_memberships( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -550,14 +553,18 @@ def list_memberships( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MembershipList) - def create_membership( self, team_id: str, @@ -566,17 +573,16 @@ def create_membership( user_id: Optional[str] = None, phone: Optional[str] = None, url: Optional[str] = None, - name: Optional[str] = None + name: Optional[str] = None, ) -> Membership: """ Invite a new member to join your team. Provide an ID for existing users, or invite unregistered users using an email or phone number. If initiated from a Client SDK, Appwrite will send an email or sms with a link to join the team to the invited user, and an account will be created for them if one doesn't exist. If initiated from a Server SDK, the new member will be added automatically to the team. - + You only need to provide one of a user ID, email, or phone number. Appwrite will prioritize accepting the user ID > email > phone number if you provide more than one of these parameters. - - Use the `url` parameter to redirect the user from the invitation email to your app. After the user is redirected, use the [Update Team Membership Status](https://appwrite.io/docs/references/cloud/client-web/teams#updateMembershipStatus) endpoint to allow the user to accept the invitation to the team. - + + Use the `url` parameter to redirect the user from the invitation email to your app. After the user is redirected, use the [Update Team Membership Status](https://appwrite.io/docs/references/cloud/client-web/teams#updateMembershipStatus) endpoint to allow the user to accept the invitation to the team. + Please note that to avoid a [Redirect Attack](https://github.com/OWASP/CheatSheetSeries/blob/master/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.md) Appwrite will accept the only redirect URLs under the domains you have added as a platform on the Appwrite Console. - Parameters ---------- @@ -594,12 +600,11 @@ def create_membership( URL to redirect the user back to your app from the invitation email. This parameter is not required when an API key is supplied. Only URLs from hostnames in your project platform list are allowed. This requirement helps to prevent an [open redirect](https://cheatsheetseries.owasp.org/cheatsheets/Unvalidated_Redirects_and_Forwards_Cheat_Sheet.html) attack against your project API. name : Optional[str] Name of the new team member. Max length: 128 chars. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -610,12 +615,9 @@ def create_membership( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if roles is None: raise AppwriteException('Missing required parameter: "roles"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - if email is not None: api_params['email'] = self._normalize_value(email) if user_id is not None: @@ -628,19 +630,23 @@ def create_membership( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def get_membership( self, team_id: str, - membership_id: str + membership_id: str, ) -> Membership: """ Get a team member by the membership unique id. All team members have read access for this resource. Hide sensitive attributes from the response by toggling membership privacy in the Console. @@ -651,12 +657,11 @@ def get_membership( Team ID. membership_id : str Membership ID. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -667,31 +672,31 @@ def get_membership( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def update_membership( self, team_id: str, membership_id: str, - roles: List[str] + roles: List[str], ) -> Membership: """ Modify the roles of a team member. Only team members with the owner role have access to this endpoint. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). - Parameters ---------- @@ -701,12 +706,11 @@ def update_membership( Membership ID. roles : List[str] An array of strings. Use this param to set the user's roles in the team. A role can be any string. Learn more about [roles and permissions](https://appwrite.io/docs/permissions). Maximum of 100 roles are allowed, each 81 characters long. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -717,31 +721,31 @@ def update_membership( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - if roles is None: raise AppwriteException('Missing required parameter: "roles"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - api_params['roles'] = self._normalize_value(roles) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def delete_membership( self, team_id: str, - membership_id: str + membership_id: str, ) -> Dict[str, Any]: """ This endpoint allows a user to leave a team or for a team owner to delete the membership of any other team member. You can also use this endpoint to delete a user membership even if it is not accepted. @@ -752,12 +756,11 @@ def delete_membership( Team ID. membership_id : str Membership ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -768,34 +771,34 @@ def delete_membership( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_membership_status( self, team_id: str, membership_id: str, user_id: str, - secret: str + secret: str, ) -> Membership: """ Use this endpoint to allow a user to accept an invitation to join a team after being redirected back to your app from the invitation email received by the user. - + If the request is successful, a session for the user is automatically created. - Parameters ---------- @@ -807,12 +810,11 @@ def update_membership_status( User ID. secret : str Secret key. - Returns ------- Membership API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -823,35 +825,34 @@ def update_membership_status( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if membership_id is None: raise AppwriteException('Missing required parameter: "membership_id"') - if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if secret is None: raise AppwriteException('Missing required parameter: "secret"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) api_path = api_path.replace('{membershipId}', str(self._normalize_value(membership_id))) - api_params['userId'] = self._normalize_value(user_id) api_params['secret'] = self._normalize_value(secret) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Membership) - def get_prefs( self, team_id: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Preferences[T]: """ Get the team's shared preferences by its unique ID. If a preference doesn't need to be shared by all team members, prefer storing them in [user preferences](https://appwrite.io/docs/references/cloud/client-web/account#getPrefs). @@ -860,15 +861,14 @@ def get_prefs( ---------- team_id : str Team ID. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Preferences[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -879,23 +879,25 @@ def get_prefs( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Preferences.with_data(response, model_type) - def update_prefs( self, team_id: str, prefs: Dict[str, Any], - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Preferences[T]: """ Update the team's preferences by its unique ID. The object you pass is stored as is and replaces any previous value. The maximum allowed prefs size is 64kB and throws an error if exceeded. @@ -906,15 +908,14 @@ def update_prefs( Team ID. prefs : Dict[str, Any] Prefs key-value JSON object. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Preferences[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -925,19 +926,20 @@ def update_prefs( api_params = {} if team_id is None: raise AppwriteException('Missing required parameter: "team_id"') - if prefs is None: raise AppwriteException('Missing required parameter: "prefs"') - api_path = api_path.replace('{teamId}', str(self._normalize_value(team_id))) - api_params['prefs'] = self._normalize_value(prefs) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Preferences.with_data(response, model_type) - diff --git a/appwrite/services/tokens.py b/appwrite/services/tokens.py index bdff3a61..d3c9eae4 100644 --- a/appwrite/services/tokens.py +++ b/appwrite/services/tokens.py @@ -6,6 +6,7 @@ from ..models.resource_token_list import ResourceTokenList from ..models.resource_token import ResourceToken + class Tokens(Service): def __init__(self, client) -> None: @@ -16,7 +17,7 @@ def list( bucket_id: str, file_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> ResourceTokenList: """ List all the tokens created for a specific file or bucket. You can use the query params to filter your results. @@ -31,12 +32,11 @@ def list( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: expire total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- ResourceTokenList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -47,31 +47,32 @@ def list( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ResourceTokenList) - def create_file_token( self, bucket_id: str, file_id: str, - expire: Optional[str] = None + expire: Optional[str] = None, ) -> ResourceToken: """ Create a new token. A token is linked to a file. Token can be passed as a request URL search parameter. @@ -84,12 +85,11 @@ def create_file_token( File unique ID. expire : Optional[str] Token expiry date - Returns ------- ResourceToken API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -100,28 +100,29 @@ def create_file_token( api_params = {} if bucket_id is None: raise AppwriteException('Missing required parameter: "bucket_id"') - if file_id is None: raise AppwriteException('Missing required parameter: "file_id"') - api_path = api_path.replace('{bucketId}', str(self._normalize_value(bucket_id))) api_path = api_path.replace('{fileId}', str(self._normalize_value(file_id))) - if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ResourceToken) - def get( self, - token_id: str + token_id: str, ) -> ResourceToken: """ Get a token by its unique ID. @@ -130,12 +131,11 @@ def get( ---------- token_id : str Token ID. - Returns ------- ResourceToken API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -146,22 +146,24 @@ def get( api_params = {} if token_id is None: raise AppwriteException('Missing required parameter: "token_id"') - api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ResourceToken) - def update( self, token_id: str, - expire: Optional[str] = None + expire: Optional[str] = None, ) -> ResourceToken: """ Update a token by its unique ID. Use this endpoint to update a token's expiry date. @@ -172,12 +174,11 @@ def update( Token unique ID. expire : Optional[str] File token expiry date - Returns ------- ResourceToken API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -188,24 +189,26 @@ def update( api_params = {} if token_id is None: raise AppwriteException('Missing required parameter: "token_id"') - api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=ResourceToken) - def delete( self, - token_id: str + token_id: str, ) -> Dict[str, Any]: """ Delete a token by its unique ID. @@ -214,12 +217,11 @@ def delete( ---------- token_id : str Token ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -230,14 +232,16 @@ def delete( api_params = {} if token_id is None: raise AppwriteException('Missing required parameter: "token_id"') - api_path = api_path.replace('{tokenId}', str(self._normalize_value(token_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - diff --git a/appwrite/services/users.py b/appwrite/services/users.py index fad7bd3c..1c7ffc67 100644 --- a/appwrite/services/users.py +++ b/appwrite/services/users.py @@ -24,6 +24,7 @@ T = TypeVar('T') + class Users(Service): def __init__(self, client) -> None: @@ -34,7 +35,7 @@ def list( queries: Optional[List[str]] = None, search: Optional[str] = None, total: Optional[bool] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> UserList[T]: """ Get a list of all the project's users. You can use the query params to filter your results. @@ -47,15 +48,14 @@ def list( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- UserList[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -64,7 +64,6 @@ def list( api_path = '/users' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -72,14 +71,18 @@ def list( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return UserList.with_data(response, model_type) - def create( self, user_id: str, @@ -87,7 +90,7 @@ def create( phone: Optional[str] = None, password: Optional[str] = None, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. @@ -104,15 +107,14 @@ def create( Plain text user password. Must be at least 8 chars. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -123,8 +125,6 @@ def create( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - - api_params['userId'] = self._normalize_value(user_id) if email is not None: api_params['email'] = self._normalize_value(email) @@ -135,22 +135,26 @@ def create( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_argon2_user( self, user_id: str, email: str, password: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [Argon2](https://en.wikipedia.org/wiki/Argon2) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -165,15 +169,14 @@ def create_argon2_user( User password hashed using Argon2. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -184,36 +187,36 @@ def create_argon2_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_bcrypt_user( self, user_id: str, email: str, password: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [Bcrypt](https://en.wikipedia.org/wiki/Bcrypt) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -228,15 +231,14 @@ def create_bcrypt_user( User password hashed using Bcrypt. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -247,34 +249,34 @@ def create_bcrypt_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def list_identities( self, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> IdentityList: """ Get identities for all users. @@ -287,12 +289,11 @@ def list_identities( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- IdentityList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -301,7 +302,6 @@ def list_identities( api_path = '/users/identities' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -309,17 +309,21 @@ def list_identities( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=IdentityList) - def delete_identity( self, - identity_id: str + identity_id: str, ) -> Dict[str, Any]: """ Delete an identity by its unique ID. @@ -328,12 +332,11 @@ def delete_identity( ---------- identity_id : str Identity ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -344,25 +347,27 @@ def delete_identity( api_params = {} if identity_id is None: raise AppwriteException('Missing required parameter: "identity_id"') - api_path = api_path.replace('{identityId}', str(self._normalize_value(identity_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_md5_user( self, user_id: str, email: str, password: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [MD5](https://en.wikipedia.org/wiki/MD5) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -377,15 +382,14 @@ def create_md5_user( User password hashed using MD5. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -396,36 +400,36 @@ def create_md5_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_ph_pass_user( self, user_id: str, email: str, password: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [PHPass](https://www.openwall.com/phpass/) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -440,15 +444,14 @@ def create_ph_pass_user( User password hashed using PHPass. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -459,29 +462,29 @@ def create_ph_pass_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_scrypt_user( self, user_id: str, @@ -493,7 +496,7 @@ def create_scrypt_user( password_parallel: float, password_length: float, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [Scrypt](https://github.com/Tarsnap/scrypt) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -518,15 +521,14 @@ def create_scrypt_user( Optional hash length used to hash password. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -537,29 +539,20 @@ def create_scrypt_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - if password_salt is None: raise AppwriteException('Missing required parameter: "password_salt"') - if password_cpu is None: raise AppwriteException('Missing required parameter: "password_cpu"') - if password_memory is None: raise AppwriteException('Missing required parameter: "password_memory"') - if password_parallel is None: raise AppwriteException('Missing required parameter: "password_parallel"') - if password_length is None: raise AppwriteException('Missing required parameter: "password_length"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) @@ -571,15 +564,19 @@ def create_scrypt_user( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_scrypt_modified_user( self, user_id: str, @@ -589,7 +586,7 @@ def create_scrypt_modified_user( password_salt_separator: str, password_signer_key: str, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [Scrypt Modified](https://gist.github.com/Meldiron/eecf84a0225eccb5a378d45bb27462cc) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -610,15 +607,14 @@ def create_scrypt_modified_user( Signer key used to hash password. name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -629,23 +625,16 @@ def create_scrypt_modified_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - if password_salt is None: raise AppwriteException('Missing required parameter: "password_salt"') - if password_salt_separator is None: raise AppwriteException('Missing required parameter: "password_salt_separator"') - if password_signer_key is None: raise AppwriteException('Missing required parameter: "password_signer_key"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) @@ -655,15 +644,19 @@ def create_scrypt_modified_user( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_sha_user( self, user_id: str, @@ -671,7 +664,7 @@ def create_sha_user( password: str, password_version: Optional[PasswordHash] = None, name: Optional[str] = None, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Create a new user. Password provided must be hashed with the [SHA](https://en.wikipedia.org/wiki/Secure_Hash_Algorithm) algorithm. Use the [POST /users](https://appwrite.io/docs/server/users#usersCreate) endpoint to create users with a plain text password. @@ -688,15 +681,14 @@ def create_sha_user( Optional SHA version used to hash password. Allowed values are: 'sha1', 'sha224', 'sha256', 'sha384', 'sha512/224', 'sha512/256', 'sha512', 'sha3-224', 'sha3-256', 'sha3-384', 'sha3-512' name : Optional[str] User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -707,14 +699,10 @@ def create_sha_user( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - - api_params['userId'] = self._normalize_value(user_id) api_params['email'] = self._normalize_value(email) api_params['password'] = self._normalize_value(password) @@ -723,19 +711,23 @@ def create_sha_user( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def get( self, user_id: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Get a user by its unique ID. @@ -744,15 +736,14 @@ def get( ---------- user_id : str User ID. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -763,21 +754,23 @@ def get( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def delete( self, - user_id: str + user_id: str, ) -> Dict[str, Any]: """ Delete a user by its unique ID, thereby releasing it's ID. Since ID is released and can be reused, all user-related resources like documents or storage files should be deleted before user deletion. If you want to keep ID reserved, use the [updateStatus](https://appwrite.io/docs/server/users#usersUpdateStatus) endpoint instead. @@ -786,12 +779,11 @@ def delete( ---------- user_id : str User ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -802,23 +794,25 @@ def delete( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_email( self, user_id: str, email: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user email by its unique ID. @@ -829,15 +823,14 @@ def update_email( User ID. email : str User email. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -848,32 +841,32 @@ def update_email( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email is None: raise AppwriteException('Missing required parameter: "email"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['email'] = self._normalize_value(email) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_impersonator( self, user_id: str, impersonator: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Enable or disable whether a user can impersonate other users. When impersonation headers are used, the request runs as the target user for API behavior, while internal audit logs still attribute the action to the original impersonator and store the impersonated target details only in internal audit payload data. - Parameters ---------- @@ -881,15 +874,14 @@ def update_impersonator( User ID. impersonator : bool Whether the user can impersonate other users. When true, the user can browse project users to choose a target and can pass impersonation headers to act as that user. Internal audit logs still attribute impersonated actions to the original impersonator and store the target user details only in internal audit payload data. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -900,28 +892,29 @@ def update_impersonator( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if impersonator is None: raise AppwriteException('Missing required parameter: "impersonator"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['impersonator'] = self._normalize_value(impersonator) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def create_jwt( self, user_id: str, session_id: Optional[str] = None, - duration: Optional[float] = None + duration: Optional[float] = None, ) -> Jwt: """ Use this endpoint to create a JSON Web Token for user by its unique ID. You can use the resulting JWT to authenticate on behalf of the user. The JWT secret will become invalid if the session it uses gets deleted. @@ -931,15 +924,14 @@ def create_jwt( user_id : str User ID. session_id : Optional[str] - Session ID. Use the string 'recent' to use the most recent session. Defaults to the most recent session. + Session ID. Use the string 'recent()' to use the most recent session, which is also the default. duration : Optional[float] Time in seconds before JWT expires. Default duration is 900 seconds, and maximum is 3600 seconds. - Returns ------- Jwt API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -950,32 +942,34 @@ def create_jwt( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if session_id is not None: api_params['sessionId'] = self._normalize_value(session_id) if duration is not None: api_params['duration'] = self._normalize_value(duration) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Jwt) - def update_labels( self, user_id: str, labels: List[str], - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ - Update the user labels by its unique ID. - + Update the user labels by its unique ID. + Labels can be used to grant access to resources. While teams are a way for user's to share access to a resource, labels can be defined by the developer to grant access without an invitation. See the [Permissions docs](https://appwrite.io/docs/permissions) for more info. Parameters @@ -984,15 +978,14 @@ def update_labels( User ID. labels : List[str] Array of user labels. Replaces the previous labels. Maximum of 1000 labels are allowed, each up to 36 alphanumeric characters long. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1003,28 +996,29 @@ def update_labels( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if labels is None: raise AppwriteException('Missing required parameter: "labels"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['labels'] = self._normalize_value(labels) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def list_logs( self, user_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> LogList: """ Get the user activity logs list by its unique ID. @@ -1037,12 +1031,11 @@ def list_logs( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Only supported methods are limit and offset total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- LogList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1053,28 +1046,30 @@ def list_logs( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=LogList) - def list_memberships( self, user_id: str, queries: Optional[List[str]] = None, search: Optional[str] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> MembershipList: """ Get the user membership list by its unique ID. @@ -1089,12 +1084,11 @@ def list_memberships( Search term to filter your list results. Max length: 256 chars. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- MembershipList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1105,9 +1099,7 @@ def list_memberships( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if search is not None: @@ -1115,19 +1107,23 @@ def list_memberships( if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MembershipList) - def update_mfa( self, user_id: str, mfa: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Enable or disable MFA on a user account. @@ -1138,15 +1134,14 @@ def update_mfa( User ID. mfa : bool Enable or disable MFA. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1157,27 +1152,28 @@ def update_mfa( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if mfa is None: raise AppwriteException('Missing required parameter: "mfa"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['mfa'] = self._normalize_value(mfa) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def delete_mfa_authenticator( self, user_id: str, - type: AuthenticatorType + type: AuthenticatorType, ) -> Dict[str, Any]: """ Delete an authenticator app. @@ -1188,12 +1184,11 @@ def delete_mfa_authenticator( User ID. type : AuthenticatorType Type of authenticator. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1204,26 +1199,27 @@ def delete_mfa_authenticator( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if type is None: raise AppwriteException('Missing required parameter: "type"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{type}', str(self._normalize_value(type))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def get_mfa_challenge( self, user_id: str, - challenge_id: str + challenge_id: str, ) -> MfaChallengeSecret: """ Get a custom MFA challenge for a user, including the code to be delivered through your own channel. @@ -1234,12 +1230,11 @@ def get_mfa_challenge( User ID. challenge_id : str ID of the challenge. - Returns ------- MfaChallengeSecret API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1250,25 +1245,26 @@ def get_mfa_challenge( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if challenge_id is None: raise AppwriteException('Missing required parameter: "challenge_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{challengeId}', str(self._normalize_value(challenge_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaChallengeSecret) - def list_mfa_factors( self, - user_id: str + user_id: str, ) -> MfaFactors: """ List the factors available on the account to be used as a MFA challange. @@ -1277,12 +1273,11 @@ def list_mfa_factors( ---------- user_id : str User ID. - Returns ------- MfaFactors API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1293,21 +1288,23 @@ def list_mfa_factors( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaFactors) - def get_mfa_recovery_codes( self, - user_id: str + user_id: str, ) -> MfaRecoveryCodes: """ Get recovery codes that can be used as backup for MFA flow by User ID. Before getting codes, they must be generated using [createMfaRecoveryCodes](/docs/references/cloud/client-web/account#createMfaRecoveryCodes) method. @@ -1316,12 +1313,11 @@ def get_mfa_recovery_codes( ---------- user_id : str User ID. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1332,21 +1328,23 @@ def get_mfa_recovery_codes( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def update_mfa_recovery_codes( self, - user_id: str + user_id: str, ) -> MfaRecoveryCodes: """ Regenerate recovery codes that can be used as backup for MFA flow by User ID. Before regenerating codes, they must be first generated using [createMfaRecoveryCodes](/docs/references/cloud/client-web/account#createMfaRecoveryCodes) method. @@ -1355,12 +1353,11 @@ def update_mfa_recovery_codes( ---------- user_id : str User ID. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1371,22 +1368,24 @@ def update_mfa_recovery_codes( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def create_mfa_recovery_codes( self, - user_id: str + user_id: str, ) -> MfaRecoveryCodes: """ Generate recovery codes used as backup for MFA flow for User ID. Recovery codes can be used as a MFA verification type in [createMfaChallenge](/docs/references/cloud/client-web/account#createMfaChallenge) method by client SDK. @@ -1395,12 +1394,11 @@ def create_mfa_recovery_codes( ---------- user_id : str User ID. - Returns ------- MfaRecoveryCodes API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1411,24 +1409,26 @@ def create_mfa_recovery_codes( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=MfaRecoveryCodes) - def update_name( self, user_id: str, name: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user name by its unique ID. @@ -1439,15 +1439,14 @@ def update_name( User ID. name : str User name. Max length: 128 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1458,28 +1457,29 @@ def update_name( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['name'] = self._normalize_value(name) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_password( self, user_id: str, password: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user password by its unique ID. @@ -1490,15 +1490,14 @@ def update_password( User ID. password : str New user password. Must be at least 8 chars. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1509,28 +1508,29 @@ def update_password( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if password is None: raise AppwriteException('Missing required parameter: "password"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['password'] = self._normalize_value(password) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_phone( self, user_id: str, number: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user phone by its unique ID. @@ -1541,15 +1541,14 @@ def update_phone( User ID. number : str User phone number. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1560,27 +1559,28 @@ def update_phone( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if number is None: raise AppwriteException('Missing required parameter: "number"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['number'] = self._normalize_value(number) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def get_prefs( self, user_id: str, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Preferences[T]: """ Get the user preferences by its unique ID. @@ -1589,15 +1589,14 @@ def get_prefs( ---------- user_id : str User ID. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Preferences[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1608,23 +1607,25 @@ def get_prefs( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return Preferences.with_data(response, model_type) - def update_prefs( self, user_id: str, prefs: Dict[str, Any], - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> Preferences[T]: """ Update the user preferences by its unique ID. The object you pass is stored as is, and replaces any previous value. The maximum allowed prefs size is 64kB and throws error if exceeded. @@ -1635,15 +1636,14 @@ def update_prefs( User ID. prefs : Dict[str, Any] Prefs key-value JSON object. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- Preferences[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1654,27 +1654,28 @@ def update_prefs( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if prefs is None: raise AppwriteException('Missing required parameter: "prefs"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['prefs'] = self._normalize_value(prefs) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return Preferences.with_data(response, model_type) - def list_sessions( self, user_id: str, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> SessionList: """ Get the user sessions list by its unique ID. @@ -1685,12 +1686,11 @@ def list_sessions( User ID. total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- SessionList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1701,39 +1701,40 @@ def list_sessions( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=SessionList) - def create_session( self, - user_id: str + user_id: str, ) -> Session: """ Creates a session for a user. Returns an immediately usable session object. - + If you want to generate a token for a custom authentication flow, use the [POST /users/{userId}/tokens](https://appwrite.io/docs/server/users#createToken) endpoint. Parameters ---------- user_id : str User ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. - Returns ------- Session API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1744,22 +1745,24 @@ def create_session( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Session) - def delete_sessions( self, - user_id: str + user_id: str, ) -> Dict[str, Any]: """ Delete all user's sessions by using the user's unique ID. @@ -1768,12 +1771,11 @@ def delete_sessions( ---------- user_id : str User ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1784,22 +1786,24 @@ def delete_sessions( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def delete_session( self, user_id: str, - session_id: str + session_id: str, ) -> Dict[str, Any]: """ Delete a user sessions by its unique ID. @@ -1810,12 +1814,11 @@ def delete_session( User ID. session_id : str Session ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -1826,27 +1829,28 @@ def delete_session( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if session_id is None: raise AppwriteException('Missing required parameter: "session_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{sessionId}', str(self._normalize_value(session_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_status( self, user_id: str, status: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user status by its unique ID. Use this endpoint as an alternative to deleting a user if you want to keep user's ID reserved. @@ -1857,15 +1861,14 @@ def update_status( User ID. status : bool User Status. To activate the user pass `true` and to block the user pass `false`. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1876,28 +1879,29 @@ def update_status( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if status is None: raise AppwriteException('Missing required parameter: "status"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['status'] = self._normalize_value(status) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def list_targets( self, user_id: str, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> TargetList: """ List the messaging targets that are associated with a user. @@ -1910,12 +1914,11 @@ def list_targets( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: userId, providerId, identifier, providerType total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- TargetList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1926,22 +1929,24 @@ def list_targets( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=TargetList) - def create_target( self, user_id: str, @@ -1949,7 +1954,7 @@ def create_target( provider_type: MessagingProviderType, identifier: str, provider_id: Optional[str] = None, - name: Optional[str] = None + name: Optional[str] = None, ) -> Target: """ Create a messaging target. @@ -1968,12 +1973,11 @@ def create_target( Provider ID. Message will be sent to this target from the specified provider ID. If no provider ID is set the first setup provider will be used. name : Optional[str] Target name. Max length: 128 chars. For example: My Awesome App Galaxy S23. - Returns ------- Target API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -1984,18 +1988,13 @@ def create_target( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if target_id is None: raise AppwriteException('Missing required parameter: "target_id"') - if provider_type is None: raise AppwriteException('Missing required parameter: "provider_type"') - if identifier is None: raise AppwriteException('Missing required parameter: "identifier"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['targetId'] = self._normalize_value(target_id) api_params['providerType'] = self._normalize_value(provider_type) api_params['identifier'] = self._normalize_value(identifier) @@ -2004,19 +2003,23 @@ def create_target( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Target) - def get_target( self, user_id: str, - target_id: str + target_id: str, ) -> Target: """ Get a user's push notification target by ID. @@ -2027,12 +2030,11 @@ def get_target( User ID. target_id : str Target ID. - Returns ------- Target API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2043,29 +2045,30 @@ def get_target( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if target_id is None: raise AppwriteException('Missing required parameter: "target_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{targetId}', str(self._normalize_value(target_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Target) - def update_target( self, user_id: str, target_id: str, identifier: Optional[str] = None, provider_id: Optional[str] = None, - name: Optional[str] = None + name: Optional[str] = None, ) -> Target: """ Update a messaging target. @@ -2082,12 +2085,11 @@ def update_target( Provider ID. Message will be sent to this target from the specified provider ID. If no provider ID is set the first setup provider will be used. name : Optional[str] Target name. Max length: 128 chars. For example: My Awesome App Galaxy S23. - Returns ------- Target API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2098,13 +2100,10 @@ def update_target( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if target_id is None: raise AppwriteException('Missing required parameter: "target_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{targetId}', str(self._normalize_value(target_id))) - if identifier is not None: api_params['identifier'] = self._normalize_value(identifier) if provider_id is not None: @@ -2112,19 +2111,23 @@ def update_target( if name is not None: api_params['name'] = self._normalize_value(name) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Target) - def delete_target( self, user_id: str, - target_id: str + target_id: str, ) -> Dict[str, Any]: """ Delete a messaging target. @@ -2135,12 +2138,11 @@ def delete_target( User ID. target_id : str Target ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -2151,31 +2153,31 @@ def delete_target( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if target_id is None: raise AppwriteException('Missing required parameter: "target_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) api_path = api_path.replace('{targetId}', str(self._normalize_value(target_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def create_token( self, user_id: str, length: Optional[float] = None, - expire: Optional[float] = None + expire: Optional[float] = None, ) -> Token: """ Returns a token with a secret key for creating a session. Use the user ID and secret and submit a request to the [PUT /account/sessions/token](https://appwrite.io/docs/references/cloud/client-web/account#createSession) endpoint to complete the login process. - Parameters ---------- @@ -2185,12 +2187,11 @@ def create_token( Token length in characters. The default length is 6 characters expire : Optional[float] Token expiration period in seconds. The default expiration is 15 minutes. - Returns ------- Token API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2201,28 +2202,30 @@ def create_token( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - if length is not None: api_params['length'] = self._normalize_value(length) if expire is not None: api_params['expire'] = self._normalize_value(expire) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Token) - def update_email_verification( self, user_id: str, email_verification: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user email verification status by its unique ID. @@ -2233,15 +2236,14 @@ def update_email_verification( User ID. email_verification : bool User email verification status. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2252,28 +2254,29 @@ def update_email_verification( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if email_verification is None: raise AppwriteException('Missing required parameter: "email_verification"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['emailVerification'] = self._normalize_value(email_verification) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - def update_phone_verification( self, user_id: str, phone_verification: bool, - model_type: Type[T] = dict + model_type: Type[T] = dict, ) -> User[T]: """ Update the user phone verification status by its unique ID. @@ -2284,15 +2287,14 @@ def update_phone_verification( User ID. phone_verification : bool User phone verification status. - model_type : Type[T], optional Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. - + Returns ------- User[T] API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -2303,19 +2305,20 @@ def update_phone_verification( api_params = {} if user_id is None: raise AppwriteException('Missing required parameter: "user_id"') - if phone_verification is None: raise AppwriteException('Missing required parameter: "phone_verification"') - api_path = api_path.replace('{userId}', str(self._normalize_value(user_id))) - api_params['phoneVerification'] = self._normalize_value(phone_verification) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return User.with_data(response, model_type) - diff --git a/appwrite/services/vectors_db.py b/appwrite/services/vectors_db.py new file mode 100644 index 00000000..e2fcba59 --- /dev/null +++ b/appwrite/services/vectors_db.py @@ -0,0 +1,2008 @@ +from ..service import Service +from urllib.parse import quote +from typing import Any, Dict, List, Optional, Union, Type, TypeVar +from ..exception import AppwriteException +from appwrite.utils.deprecated import deprecated +from ..models.database_list import DatabaseList +from ..models.database import Database +from ..models.dedicated_database_specification_list import DedicatedDatabaseSpecificationList +from ..models.transaction_list import TransactionList +from ..models.transaction import Transaction +from ..models.vectorsdb_collection_list import VectorsdbCollectionList +from ..models.vectorsdb_collection import VectorsdbCollection +from ..models.document_list import DocumentList +from ..models.document import Document +from ..models.index_list import IndexList +from ..enums.vectors_db_index_type import VectorsDBIndexType +from ..enums.order_by import OrderBy +from ..models.index import Index +from ..models.dedicated_database import DedicatedDatabase +from ..models.dedicated_database_operation_list import DedicatedDatabaseOperationList +from ..models.dedicated_database_replicas import DedicatedDatabaseReplicas +from ..models.database_status import DatabaseStatus + +T = TypeVar('T') + + +class VectorsDB(Service): + + def __init__(self, client) -> None: + super(VectorsDB, self).__init__(client) + + def list( + self, + queries: Optional[List[str]] = None, + total: Optional[bool] = None, + ) -> DatabaseList: + """ + Get a list of all databases from the current Appwrite project. You can use the search parameter to filter your results. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following columns: name + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + DatabaseList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseList) + + def create( + self, + database_id: str, + name: str, + enabled: Optional[bool] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + ) -> Database: + """ + Create a new Database. + + Parameters + ---------- + database_id : str + Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Database name. Max length: 128 chars. + enabled : Optional[bool] + Is the database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + specification : Optional[str] + Database specification. Defaults to `serverless`, which creates the database on the shared pool. Any other value provisions a dedicated database on that specification. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Requires a dedicated `specification`; must be 0 for a serverless database. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Requires a dedicated `specification`; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_params['databaseId'] = self._normalize_value(database_id) + api_params['name'] = self._normalize_value(name) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def list_specifications( + self, + ) -> DedicatedDatabaseSpecificationList: + """ + List the dedicated database specifications available on the current plan. Each specification reports its resource limits, pricing, and whether it is enabled for the organization. + Returns + ------- + DedicatedDatabaseSpecificationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/specifications' + api_params = {} + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseSpecificationList) + + def list_transactions( + self, + queries: Optional[List[str]] = None, + ) -> TransactionList: + """ + List transactions across all databases. + + Parameters + ---------- + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). + Returns + ------- + TransactionList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions' + api_params = {} + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=TransactionList) + + def create_transaction( + self, + ttl: Optional[float] = None, + ) -> Transaction: + """ + Create a new transaction. + + Parameters + ---------- + ttl : Optional[float] + Seconds before the transaction expires. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions' + api_params = {} + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def get_transaction( + self, + transaction_id: str, + ) -> Transaction: + """ + Get a transaction by its unique ID. + + Parameters + ---------- + transaction_id : str + Transaction ID. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def update_transaction( + self, + transaction_id: str, + commit: Optional[bool] = None, + rollback: Optional[bool] = None, + ) -> Transaction: + """ + Update a transaction, to either commit or roll back its operations. + + Parameters + ---------- + transaction_id : str + Transaction ID. + commit : Optional[bool] + Commit transaction? + rollback : Optional[bool] + Rollback transaction? + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + if commit is not None: + api_params['commit'] = self._normalize_value(commit) + if rollback is not None: + api_params['rollback'] = self._normalize_value(rollback) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def delete_transaction( + self, + transaction_id: str, + ) -> Dict[str, Any]: + """ + Delete a transaction by its unique ID. + + Parameters + ---------- + transaction_id : str + Transaction ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions/{transactionId}' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def create_operations( + self, + transaction_id: str, + operations: Optional[List[Dict[str, Any]]] = None, + ) -> Transaction: + """ + Create multiple operations in a single transaction. + + Parameters + ---------- + transaction_id : str + Transaction ID. + operations : Optional[List[Dict[str, Any]]] + Array of staged operations. + Returns + ------- + Transaction + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/transactions/{transactionId}/operations' + api_params = {} + if transaction_id is None: + raise AppwriteException('Missing required parameter: "transaction_id"') + api_path = api_path.replace('{transactionId}', str(self._normalize_value(transaction_id))) + if operations is not None: + api_params['operations'] = self._normalize_value(operations) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Transaction) + + def get( + self, + database_id: str, + ) -> Database: + """ + Get a database by its unique ID. This endpoint response returns a JSON object with the database metadata. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def update( + self, + database_id: str, + name: str, + enabled: Optional[bool] = None, + specification: Optional[str] = None, + replicas: Optional[float] = None, + sync_mode: Optional[str] = None, + ) -> Database: + """ + Update a database by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + name : str + Database name. Max length: 128 chars. + enabled : Optional[bool] + Is database enabled? When set to 'disabled', users cannot access the database but Server SDKs with an API key can still read and write to the database. No data is lost when this is toggled. + specification : Optional[str] + Database specification. Resizing between dedicated specifications changes cpu, memory, storage and the connection ceiling via a rolling cutover with zero downtime. Moving a `serverless` database onto a dedicated specification is a data migration, not a resize. + replicas : Optional[float] + Number of high availability replicas (0-5) for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification. High availability is enabled when greater than 0. + sync_mode : Optional[str] + Replication sync mode for the dedicated database backing this database. Only valid when the database is backed by a dedicated specification; the mode is only in force once there is at least one replica. Allowed values: async, sync, quorum. + Returns + ------- + Database + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['name'] = self._normalize_value(name) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + if specification is not None: + api_params['specification'] = self._normalize_value(specification) + if replicas is not None: + api_params['replicas'] = self._normalize_value(replicas) + if sync_mode is not None: + api_params['syncMode'] = self._normalize_value(sync_mode) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Database) + + def delete( + self, + database_id: str, + ) -> Dict[str, Any]: + """ + Delete a database by its unique ID. Only API keys with with databases.write scope can delete a database. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def list_collections( + self, + database_id: str, + queries: Optional[List[str]] = None, + search: Optional[str] = None, + total: Optional[bool] = None, + ) -> VectorsdbCollectionList: + """ + Get a list of all collections that belong to the provided databaseId. You can use the search parameter to filter your results. + + Parameters + ---------- + database_id : str + Database ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, enabled, documentSecurity + search : Optional[str] + Search term to filter your list results. Max length: 256 chars. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + VectorsdbCollectionList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if search is not None: + api_params['search'] = self._normalize_value(search) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=VectorsdbCollectionList) + + def create_collection( + self, + database_id: str, + collection_id: str, + name: str, + dimension: float, + permissions: Optional[List[str]] = None, + document_security: Optional[bool] = None, + enabled: Optional[bool] = None, + ) -> VectorsdbCollection: + """ + Create a new Collection. Before using this route, you should create a new database resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Unique Id. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + name : str + Collection name. Max length: 128 chars. + dimension : float + Embedding dimension. + permissions : Optional[List[str]] + An array of permissions strings. By default, no user is granted with any permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + document_security : Optional[bool] + Enables configuring permissions for individual documents. A user needs one of document or collection level permissions to access a document. [Learn more about permissions](https://appwrite.io/docs/permissions). + enabled : Optional[bool] + Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. + Returns + ------- + VectorsdbCollection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + if dimension is None: + raise AppwriteException('Missing required parameter: "dimension"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_params['collectionId'] = self._normalize_value(collection_id) + api_params['name'] = self._normalize_value(name) + api_params['dimension'] = self._normalize_value(dimension) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if document_security is not None: + api_params['documentSecurity'] = self._normalize_value(document_security) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=VectorsdbCollection) + + def get_collection( + self, + database_id: str, + collection_id: str, + ) -> VectorsdbCollection: + """ + Get a collection by its unique ID. This endpoint response returns a JSON object with the collection metadata. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + Returns + ------- + VectorsdbCollection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=VectorsdbCollection) + + def update_collection( + self, + database_id: str, + collection_id: str, + name: str, + dimension: Optional[float] = None, + permissions: Optional[List[str]] = None, + document_security: Optional[bool] = None, + enabled: Optional[bool] = None, + ) -> VectorsdbCollection: + """ + Update a collection by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + name : str + Collection name. Max length: 128 chars. + dimension : Optional[float] + Embedding dimensions. + permissions : Optional[List[str]] + An array of permission strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + document_security : Optional[bool] + Enables configuring permissions for individual documents. A user needs one of document or collection level permissions to access a document. [Learn more about permissions](https://appwrite.io/docs/permissions). + enabled : Optional[bool] + Is collection enabled? When set to 'disabled', users cannot access the collection but Server SDKs with and API key can still read and write to the collection. No data is lost when this is toggled. + Returns + ------- + VectorsdbCollection + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if name is None: + raise AppwriteException('Missing required parameter: "name"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['name'] = self._normalize_value(name) + if dimension is not None: + api_params['dimension'] = self._normalize_value(dimension) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if document_security is not None: + api_params['documentSecurity'] = self._normalize_value(document_security) + if enabled is not None: + api_params['enabled'] = self._normalize_value(enabled) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=VectorsdbCollection) + + def delete_collection( + self, + database_id: str, + collection_id: str, + ) -> Dict[str, Any]: + """ + Delete a collection by its unique ID. Only users with write permissions have access to delete this resource. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def list_documents( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + total: Optional[bool] = None, + ttl: Optional[float] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Get a list of all the user's documents in a given collection. You can use the query params to filter your results. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 524288 characters long. + transaction_id : Optional[str] + Transaction ID to read uncommitted changes within the transaction. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + ttl : Optional[float] + TTL (seconds) for cached responses when caching is enabled for select queries. Must be between 0 and 86400 (24 hours). + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + if total is not None: + api_params['total'] = self._normalize_value(total) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def create_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Dict[str, Any], + permissions: Optional[List[str]] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Create a new Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). Make sure to define attributes before creating documents. + document_id : str + Document ID. Choose a custom ID or generate a random ID with `ID.unique()`. Valid chars are a-z, A-Z, 0-9, period, hyphen, and underscore. Can't start with a special char. Max length is 36 chars. + data : Dict[str, Any] + Document data as JSON object. + permissions : Optional[List[str]] + An array of permissions strings. By default, only the current user is granted all permissions. [Learn more about permissions](https://appwrite.io/docs/permissions). + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + if data is None: + raise AppwriteException('Missing required parameter: "data"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documentId'] = self._normalize_value(document_id) + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def create_documents( + self, + database_id: str, + collection_id: str, + documents: List[Dict[str, Any]], + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Create new Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). Make sure to define attributes before creating documents. + documents : List[Dict[str, Any]] + Array of documents data as JSON objects. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if documents is None: + raise AppwriteException('Missing required parameter: "documents"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documents'] = self._normalize_value(documents) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def upsert_documents( + self, + database_id: str, + collection_id: str, + documents: List[Dict[str, Any]], + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Create or update Documents. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + documents : List[Dict[str, Any]] + Array of document data as JSON objects. May contain partial documents. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if documents is None: + raise AppwriteException('Missing required parameter: "documents"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['documents'] = self._normalize_value(documents) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def update_documents( + self, + database_id: str, + collection_id: str, + data: Optional[Dict[str, Any]] = None, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Update all documents that match your queries, if no queries are submitted then all documents are updated. You can pass only specific fields to be updated. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include only attribute and value pairs to be updated. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def delete_documents( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Bulk delete documents using queries, if no queries are passed then all documents are deleted. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def create_query( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + total: Optional[bool] = None, + ttl: Optional[float] = None, + model_type: Type[T] = dict, + ) -> DocumentList[T]: + """ + Get a list of all the user's documents in a given collection using a POST request. This behaves identically to the list documents endpoint but accepts the queries in the request body, allowing much larger `queries` arrays than can fit in a URL query string. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 524288 characters long. + transaction_id : Optional[str] + Transaction ID to read uncommitted changes within the transaction. + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + ttl : Optional[float] + TTL (seconds) for cached responses when caching is enabled for select queries. Must be between 0 and 86400 (24 hours). + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + DocumentList[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents/query' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + if total is not None: + api_params['total'] = self._normalize_value(total) + if ttl is not None: + api_params['ttl'] = self._normalize_value(ttl) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return DocumentList.with_data(response, model_type) + + def get_document( + self, + database_id: str, + collection_id: str, + document_id: str, + queries: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Get a document by its unique ID. This endpoint response returns a JSON object with the document data. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + document_id : str + Document ID. + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. + transaction_id : Optional[str] + Transaction ID to read uncommitted changes within the transaction. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def upsert_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Optional[Dict[str, Any]] = None, + permissions: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Create or update a Document. Before using this route, you should create a new collection resource using either a [server integration](https://appwrite.io/docs/server/databases#documentsDBCreateCollection) API or directly from your database console. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include all required fields of the document to be created or updated. + permissions : Optional[List[str]] + An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def update_document( + self, + database_id: str, + collection_id: str, + document_id: str, + data: Optional[Dict[str, Any]] = None, + permissions: Optional[List[str]] = None, + transaction_id: Optional[str] = None, + model_type: Type[T] = dict, + ) -> Document[T]: + """ + Update a document by its unique ID. Using the patch method you can pass only specific fields that will get updated. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. + document_id : str + Document ID. + data : Optional[Dict[str, Any]] + Document data as JSON object. Include only fields and value pairs to be updated. + permissions : Optional[List[str]] + An array of permissions strings. By default, the current permissions are inherited. [Learn more about permissions](https://appwrite.io/docs/permissions). + transaction_id : Optional[str] + Transaction ID for staging the operation. + model_type : Type[T], optional + Pydantic model class for the user-defined data. Defaults to dict for backward compatibility. + + Returns + ------- + Document[T] + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if data is not None: + api_params['data'] = self._normalize_value(data) + if permissions is not None: + api_params['permissions'] = self._normalize_value(permissions) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return Document.with_data(response, model_type) + + def delete_document( + self, + database_id: str, + collection_id: str, + document_id: str, + transaction_id: Optional[str] = None, + ) -> Dict[str, Any]: + """ + Delete a document by its unique ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + document_id : str + Document ID. + transaction_id : Optional[str] + Transaction ID for staging the operation. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/documents/{documentId}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if document_id is None: + raise AppwriteException('Missing required parameter: "document_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{documentId}', str(self._normalize_value(document_id))) + if transaction_id is not None: + api_params['transactionId'] = self._normalize_value(transaction_id) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def list_indexes( + self, + database_id: str, + collection_id: str, + queries: Optional[List[str]] = None, + total: Optional[bool] = None, + ) -> IndexList: + """ + List indexes in the collection. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + queries : Optional[List[str]] + Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: key, type, status, attributes, error + total : Optional[bool] + When set to false, the total count returned will be 0 and will not be calculated. + Returns + ------- + IndexList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/indexes' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + if queries is not None: + api_params['queries'] = self._normalize_value(queries) + if total is not None: + api_params['total'] = self._normalize_value(total) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=IndexList) + + def create_index( + self, + database_id: str, + collection_id: str, + key: str, + type: VectorsDBIndexType, + attributes: List[str], + orders: Optional[List[OrderBy]] = None, + lengths: Optional[List[float]] = None, + ) -> Index: + """ + Creates an index on the attributes listed. Your index should include all the attributes you will query in a single request. + Attributes can be `key`, `fulltext`, and `unique`. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + type : VectorsDBIndexType + Index type. + attributes : List[str] + Array of attributes to index. Maximum of 100 attributes are allowed, each 32 characters long. + orders : Optional[List[OrderBy]] + Array of index orders. Maximum of 100 orders are allowed. + lengths : Optional[List[float]] + Length of index. Maximum of 100 + Returns + ------- + Index + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/indexes' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + if type is None: + raise AppwriteException('Missing required parameter: "type"') + if attributes is None: + raise AppwriteException('Missing required parameter: "attributes"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_params['key'] = self._normalize_value(key) + api_params['type'] = self._normalize_value(type) + api_params['attributes'] = self._normalize_value(attributes) + if orders is not None: + api_params['orders'] = self._normalize_value(orders) + if lengths is not None: + api_params['lengths'] = self._normalize_value(lengths) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Index) + + def get_index( + self, + database_id: str, + collection_id: str, + key: str, + ) -> Index: + """ + Get index by ID. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + Returns + ------- + Index + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/indexes/{key}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{key}', str(self._normalize_value(key))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=Index) + + def delete_index( + self, + database_id: str, + collection_id: str, + key: str, + ) -> Dict[str, Any]: + """ + Delete an index. + + Parameters + ---------- + database_id : str + Database ID. + collection_id : str + Collection ID. You can create a new collection using the Database service [server integration](https://appwrite.io/docs/server/databases#databasesCreateCollection). + key : str + Index Key. + Returns + ------- + Dict[str, Any] + API response as a dictionary + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/collections/{collectionId}/indexes/{key}' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + if collection_id is None: + raise AppwriteException('Missing required parameter: "collection_id"') + if key is None: + raise AppwriteException('Missing required parameter: "key"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + api_path = api_path.replace('{collectionId}', str(self._normalize_value(collection_id))) + api_path = api_path.replace('{key}', str(self._normalize_value(key))) + + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) + + return response + + def create_failover( + self, + database_id: str, + target_replica_id: Optional[str] = None, + ) -> DedicatedDatabase: + """ + Trigger a manual failover for a dedicated database with high availability enabled. Promotes a replica to primary. The failover runs asynchronously; poll the database document for status updates. A database left mid-operation also accepts this call as a repair once nothing is driving the operation it is stuck in. Repairing a failover that did not finish, a `failed` database, a stranded upgrade or migrate, or a stranded compute resize additionally requires `targetReplicaId` to name the member to promote, because the default target may be the member that operation already promoted. + + Parameters + ---------- + database_id : str + Database ID. + target_replica_id : Optional[str] + Target replica ID to promote. If not specified, the healthiest replica is selected. + Returns + ------- + DedicatedDatabase + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/failovers' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if target_replica_id is not None: + api_params['targetReplicaId'] = self._normalize_value(target_replica_id) + + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabase) + + def list_operations( + self, + database_id: str, + status: Optional[str] = None, + limit: Optional[float] = None, + offset: Optional[float] = None, + ) -> DedicatedDatabaseOperationList: + """ + List the lifecycle operations recorded for a dedicated database, newest first. Every provision, update, restore, backup and replication action is recorded here with its outcome, including an attempt that was abandoned because another worker took over the database. + + Parameters + ---------- + database_id : str + Database ID. + status : Optional[str] + Filter by operation status. + limit : Optional[float] + Maximum number of operations to return. + offset : Optional[float] + Number of operations to skip. + Returns + ------- + DedicatedDatabaseOperationList + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/operations' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + if status is not None: + api_params['status'] = self._normalize_value(status) + if limit is not None: + api_params['limit'] = self._normalize_value(limit) + if offset is not None: + api_params['offset'] = self._normalize_value(offset) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseOperationList) + + def get_replicas( + self, + database_id: str, + ) -> DedicatedDatabaseReplicas: + """ + Get high availability status for a dedicated database. Returns replica statuses, replication lag, and sync mode. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DedicatedDatabaseReplicas + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/replicas' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DedicatedDatabaseReplicas) + + def get_status( + self, + database_id: str, + ) -> DatabaseStatus: + """ + Get real-time health and status information for a dedicated database. Returns health status, readiness, uptime, connection info, replica status, and volume information. + + Parameters + ---------- + database_id : str + Database ID. + Returns + ------- + DatabaseStatus + API response as a typed Pydantic model + + Raises + ------ + AppwriteException + If API request fails + """ + + api_path = '/vectorsdb/{databaseId}/status' + api_params = {} + if database_id is None: + raise AppwriteException('Missing required parameter: "database_id"') + api_path = api_path.replace('{databaseId}', str(self._normalize_value(database_id))) + + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) + + return self._parse_response(response, model=DatabaseStatus) diff --git a/appwrite/services/webhooks.py b/appwrite/services/webhooks.py index 9e998f36..16674e2c 100644 --- a/appwrite/services/webhooks.py +++ b/appwrite/services/webhooks.py @@ -6,6 +6,7 @@ from ..models.webhook_list import WebhookList from ..models.webhook import Webhook + class Webhooks(Service): def __init__(self, client) -> None: @@ -14,7 +15,7 @@ def __init__(self, client) -> None: def list( self, queries: Optional[List[str]] = None, - total: Optional[bool] = None + total: Optional[bool] = None, ) -> WebhookList: """ Get a list of all webhooks belonging to the project. You can use the query params to filter your results. @@ -25,12 +26,11 @@ def list( Array of query strings generated using the Query class provided by the SDK. [Learn more about queries](https://appwrite.io/docs/queries). Maximum of 100 queries are allowed, each 4096 characters long. You may filter on the following attributes: name, url, authUsername, tls, events, enabled, logs, attempts total : Optional[bool] When set to false, the total count returned will be 0 and will not be calculated. - Returns ------- WebhookList API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -39,20 +39,23 @@ def list( api_path = '/webhooks' api_params = {} - if queries is not None: api_params['queries'] = self._normalize_value(queries) if total is not None: api_params['total'] = self._normalize_value(total) - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=WebhookList) - def create( self, webhook_id: str, @@ -63,7 +66,7 @@ def create( tls: Optional[bool] = None, auth_username: Optional[str] = None, auth_password: Optional[str] = None, - secret: Optional[str] = None + secret: Optional[str] = None, ) -> Webhook: """ Create a new webhook. Use this endpoint to configure a URL that will receive events from Appwrite when specific events occur. @@ -88,12 +91,11 @@ def create( Webhook HTTP password. Max length: 256 chars. secret : Optional[str] Webhook secret key. If not provided, a new key will be generated automatically. Key must be at least 8 characters long, and at max 256 characters. - Returns ------- Webhook API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -104,17 +106,12 @@ def create( api_params = {} if webhook_id is None: raise AppwriteException('Missing required parameter: "webhook_id"') - if url is None: raise AppwriteException('Missing required parameter: "url"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if events is None: raise AppwriteException('Missing required parameter: "events"') - - api_params['webhookId'] = self._normalize_value(webhook_id) api_params['url'] = self._normalize_value(url) api_params['name'] = self._normalize_value(name) @@ -130,32 +127,35 @@ def create( if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('post', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'post', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Webhook) - def get( self, - webhook_id: str + webhook_id: str, ) -> Webhook: """ - Get a webhook by its unique ID. This endpoint returns details about a specific webhook configured for a project. + Get a webhook by its unique ID. This endpoint returns details about a specific webhook configured for a project. Parameters ---------- webhook_id : str Webhook ID. - Returns ------- Webhook API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -166,18 +166,20 @@ def get( api_params = {} if webhook_id is None: raise AppwriteException('Missing required parameter: "webhook_id"') - api_path = api_path.replace('{webhookId}', str(self._normalize_value(webhook_id))) - - response = self.client.call('get', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'get', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Webhook) - def update( self, webhook_id: str, @@ -187,7 +189,7 @@ def update( enabled: Optional[bool] = None, tls: Optional[bool] = None, auth_username: Optional[str] = None, - auth_password: Optional[str] = None + auth_password: Optional[str] = None, ) -> Webhook: """ Update a webhook by its unique ID. Use this endpoint to update the URL, events, or status of an existing webhook. @@ -210,12 +212,11 @@ def update( Webhook HTTP user. Max length: 256 chars. auth_password : Optional[str] Webhook HTTP password. Max length: 256 chars. - Returns ------- Webhook API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -226,18 +227,13 @@ def update( api_params = {} if webhook_id is None: raise AppwriteException('Missing required parameter: "webhook_id"') - if name is None: raise AppwriteException('Missing required parameter: "name"') - if url is None: raise AppwriteException('Missing required parameter: "url"') - if events is None: raise AppwriteException('Missing required parameter: "events"') - api_path = api_path.replace('{webhookId}', str(self._normalize_value(webhook_id))) - api_params['name'] = self._normalize_value(name) api_params['url'] = self._normalize_value(url) api_params['events'] = self._normalize_value(events) @@ -250,32 +246,35 @@ def update( if auth_password is not None: api_params['authPassword'] = self._normalize_value(auth_password) - response = self.client.call('put', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'put', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Webhook) - def delete( self, - webhook_id: str + webhook_id: str, ) -> Dict[str, Any]: """ - Delete a webhook by its unique ID. Once deleted, the webhook will no longer receive project events. + Delete a webhook by its unique ID. Once deleted, the webhook will no longer receive project events. Parameters ---------- webhook_id : str Webhook ID. - Returns ------- Dict[str, Any] API response as a dictionary - + Raises ------ AppwriteException @@ -286,22 +285,24 @@ def delete( api_params = {} if webhook_id is None: raise AppwriteException('Missing required parameter: "webhook_id"') - api_path = api_path.replace('{webhookId}', str(self._normalize_value(webhook_id))) - - response = self.client.call('delete', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - }, api_params) + response = self.client.call( + 'delete', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + }, + api_params, + ) return response - def update_secret( self, webhook_id: str, - secret: Optional[str] = None + secret: Optional[str] = None, ) -> Webhook: """ Update the webhook signing key. This endpoint can be used to regenerate the signing key used to sign and validate payload deliveries for a specific webhook. @@ -312,12 +313,11 @@ def update_secret( Webhook ID. secret : Optional[str] Webhook secret key. If not provided, a new key will be generated automatically. Key must be at least 8 characters long, and at max 256 characters. - Returns ------- Webhook API response as a typed Pydantic model - + Raises ------ AppwriteException @@ -328,17 +328,19 @@ def update_secret( api_params = {} if webhook_id is None: raise AppwriteException('Missing required parameter: "webhook_id"') - api_path = api_path.replace('{webhookId}', str(self._normalize_value(webhook_id))) - if secret is not None: api_params['secret'] = self._normalize_value(secret) - response = self.client.call('patch', api_path, { - 'X-Appwrite-Project': self.client.get_config('project'), - 'content-type': 'application/json', - 'accept': 'application/json', - }, api_params) + response = self.client.call( + 'patch', + api_path, + { + 'X-Appwrite-Project': self.client.get_config('project'), + 'content-type': 'application/json', + 'accept': 'application/json', + }, + api_params, + ) return self._parse_response(response, model=Webhook) - diff --git a/appwrite/utils/deprecated.py b/appwrite/utils/deprecated.py index 0e0e6e6e..d384ec0d 100644 --- a/appwrite/utils/deprecated.py +++ b/appwrite/utils/deprecated.py @@ -8,6 +8,7 @@ import functools import warnings + def deprecated(reason=None): """ Decorator to mark functions as deprecated. @@ -21,24 +22,19 @@ def deprecated(reason=None): def old_function(...): ... """ + def decorator(func): - message = "Call to deprecated function '{}'.{}".format( - func.__name__, - " " + reason if reason else "" - ) + message = "Call to deprecated function '{}'.{}".format(func.__name__, " " + reason if reason else "") @functools.wraps(func) def wrapped(*args, **kwargs): - warnings.simplefilter('always', DeprecationWarning) # show warning every time + warnings.simplefilter('always', DeprecationWarning) # show warning every time try: - warnings.warn( - message, - category=DeprecationWarning, - stacklevel=2 - ) + warnings.warn(message, category=DeprecationWarning, stacklevel=2) return func(*args, **kwargs) finally: warnings.simplefilter('default', DeprecationWarning) # reset filter + return wrapped # Support both @deprecated and @deprecated("reason") diff --git a/docs/examples/avatars/get-initials.md b/docs/examples/avatars/get-initials.md index 30a39a8e..08788555 100644 --- a/docs/examples/avatars/get-initials.md +++ b/docs/examples/avatars/get-initials.md @@ -13,6 +13,6 @@ result: bytes = avatars.get_initials( name = '', # optional width = 0, # optional height = 0, # optional - background = '' # optional + background = 'FFFFFF' # optional ) ``` diff --git a/docs/examples/avatars/get-photo.md b/docs/examples/avatars/get-photo.md new file mode 100644 index 00000000..64cdf309 --- /dev/null +++ b/docs/examples/avatars/get-photo.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.avatars import Avatars + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +avatars = Avatars(client) + +result: bytes = avatars.get_photo( + width = 0, # optional + height = 0, # optional + quality = 0, # optional + output = 'png', # optional + rating = 'g', # optional + user_id = 'current()', # optional + email_hash = '', # optional + name = '' # optional +) +``` diff --git a/docs/examples/databases/create-big-int-attribute.md b/docs/examples/databases/create-big-int-attribute.md index 8c615d9f..e55ab28c 100644 --- a/docs/examples/databases/create-big-int-attribute.md +++ b/docs/examples/databases/create-big-int-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeBigint = databases.create_big_int_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 1000000, # optional + default = 0, # optional array = False # optional ) diff --git a/docs/examples/databases/create-boolean-attribute.md b/docs/examples/databases/create-boolean-attribute.md index b18196d7..7c66b322 100644 --- a/docs/examples/databases/create-boolean-attribute.md +++ b/docs/examples/databases/create-boolean-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributeBoolean = databases.create_boolean_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = False, # optional array = False # optional diff --git a/docs/examples/databases/create-datetime-attribute.md b/docs/examples/databases/create-datetime-attribute.md index 9ee99ca2..d6e5a437 100644 --- a/docs/examples/databases/create-datetime-attribute.md +++ b/docs/examples/databases/create-datetime-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributeDatetime = databases.create_datetime_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = '2020-10-15T06:38:00.000+00:00', # optional array = False # optional diff --git a/docs/examples/databases/create-email-attribute.md b/docs/examples/databases/create-email-attribute.md index 8c37eff0..8330bb9a 100644 --- a/docs/examples/databases/create-email-attribute.md +++ b/docs/examples/databases/create-email-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributeEmail = databases.create_email_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = 'email@example.com', # optional array = False # optional diff --git a/docs/examples/databases/create-enum-attribute.md b/docs/examples/databases/create-enum-attribute.md index bc8a4ab7..4710819f 100644 --- a/docs/examples/databases/create-enum-attribute.md +++ b/docs/examples/databases/create-enum-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeEnum = databases.create_enum_attribute( database_id = '', collection_id = '', - key = '', - elements = [], + key = '', + elements = ["active", "inactive"], required = False, - default = '', # optional + default = 'active', # optional array = False # optional ) diff --git a/docs/examples/databases/create-float-attribute.md b/docs/examples/databases/create-float-attribute.md index 204dbfdb..e7155081 100644 --- a/docs/examples/databases/create-float-attribute.md +++ b/docs/examples/databases/create-float-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeFloat = databases.create_float_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 100, # optional + default = 10.5, # optional array = False # optional ) diff --git a/docs/examples/databases/create-index.md b/docs/examples/databases/create-index.md index e973ae0b..71c694f1 100644 --- a/docs/examples/databases/create-index.md +++ b/docs/examples/databases/create-index.md @@ -15,7 +15,7 @@ databases = Databases(client) result: Index = databases.create_index( database_id = '', collection_id = '', - key = '', + key = '', type = DatabasesIndexType.KEY, attributes = [], orders = [OrderBy.ASC], # optional diff --git a/docs/examples/databases/create-integer-attribute.md b/docs/examples/databases/create-integer-attribute.md index fe609ba4..c46e2295 100644 --- a/docs/examples/databases/create-integer-attribute.md +++ b/docs/examples/databases/create-integer-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeInteger = databases.create_integer_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 100, # optional + default = 10, # optional array = False # optional ) diff --git a/docs/examples/databases/create-ip-attribute.md b/docs/examples/databases/create-ip-attribute.md index c684df57..34542fa9 100644 --- a/docs/examples/databases/create-ip-attribute.md +++ b/docs/examples/databases/create-ip-attribute.md @@ -13,9 +13,9 @@ databases = Databases(client) result: AttributeIp = databases.create_ip_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = '192.0.2.0', # optional array = False # optional ) diff --git a/docs/examples/databases/create-line-attribute.md b/docs/examples/databases/create-line-attribute.md index 5a782767..6745498a 100644 --- a/docs/examples/databases/create-line-attribute.md +++ b/docs/examples/databases/create-line-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributeLine = databases.create_line_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [[1, 2], [3, 4], [5, 6]] # optional ) diff --git a/docs/examples/databases/create-longtext-attribute.md b/docs/examples/databases/create-longtext-attribute.md index 7659fadb..70b0eb48 100644 --- a/docs/examples/databases/create-longtext-attribute.md +++ b/docs/examples/databases/create-longtext-attribute.md @@ -13,9 +13,9 @@ databases = Databases(client) result: AttributeLongtext = databases.create_longtext_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/databases/create-mediumtext-attribute.md b/docs/examples/databases/create-mediumtext-attribute.md index f7381b2a..cf3011ac 100644 --- a/docs/examples/databases/create-mediumtext-attribute.md +++ b/docs/examples/databases/create-mediumtext-attribute.md @@ -13,9 +13,9 @@ databases = Databases(client) result: AttributeMediumtext = databases.create_mediumtext_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/databases/create-point-attribute.md b/docs/examples/databases/create-point-attribute.md index 8b8c8d1a..a3d12715 100644 --- a/docs/examples/databases/create-point-attribute.md +++ b/docs/examples/databases/create-point-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributePoint = databases.create_point_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [1, 2] # optional ) diff --git a/docs/examples/databases/create-polygon-attribute.md b/docs/examples/databases/create-polygon-attribute.md index defb0e94..4e6145f5 100644 --- a/docs/examples/databases/create-polygon-attribute.md +++ b/docs/examples/databases/create-polygon-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributePolygon = databases.create_polygon_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [[[1, 2], [3, 4], [5, 6], [1, 2]]] # optional ) diff --git a/docs/examples/databases/create-relationship-attribute.md b/docs/examples/databases/create-relationship-attribute.md index b4300dd2..81959496 100644 --- a/docs/examples/databases/create-relationship-attribute.md +++ b/docs/examples/databases/create-relationship-attribute.md @@ -18,8 +18,8 @@ result: AttributeRelationship = databases.create_relationship_attribute( related_collection_id = '', type = RelationshipType.ONETOONE, two_way = False, # optional - key = '', # optional - two_way_key = '', # optional + key = '', # optional + two_way_key = '', # optional on_delete = RelationMutate.CASCADE # optional ) diff --git a/docs/examples/databases/create-string-attribute.md b/docs/examples/databases/create-string-attribute.md index 9d1383d6..84089243 100644 --- a/docs/examples/databases/create-string-attribute.md +++ b/docs/examples/databases/create-string-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeString = databases.create_string_attribute( database_id = '', collection_id = '', - key = '', + key = '', size = 1, required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/databases/create-text-attribute.md b/docs/examples/databases/create-text-attribute.md index 89f29e2b..195650ee 100644 --- a/docs/examples/databases/create-text-attribute.md +++ b/docs/examples/databases/create-text-attribute.md @@ -13,9 +13,9 @@ databases = Databases(client) result: AttributeText = databases.create_text_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/databases/create-url-attribute.md b/docs/examples/databases/create-url-attribute.md index b6e773ac..2fdaadac 100644 --- a/docs/examples/databases/create-url-attribute.md +++ b/docs/examples/databases/create-url-attribute.md @@ -13,7 +13,7 @@ databases = Databases(client) result: AttributeUrl = databases.create_url_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = 'https://example.com', # optional array = False # optional diff --git a/docs/examples/databases/create-varchar-attribute.md b/docs/examples/databases/create-varchar-attribute.md index 964e2fc3..b0a32221 100644 --- a/docs/examples/databases/create-varchar-attribute.md +++ b/docs/examples/databases/create-varchar-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeVarchar = databases.create_varchar_attribute( database_id = '', collection_id = '', - key = '', + key = '', size = 1, required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/databases/decrement-document-attribute.md b/docs/examples/databases/decrement-document-attribute.md index c7bbfdd1..15a42ec3 100644 --- a/docs/examples/databases/decrement-document-attribute.md +++ b/docs/examples/databases/decrement-document-attribute.md @@ -14,9 +14,9 @@ result: Document = databases.decrement_document_attribute( database_id = '', collection_id = '', document_id = '', - attribute = '', - value = None, # optional - min = None, # optional + attribute = '', + value = 1, # optional + min = 0, # optional transaction_id = '' # optional ) diff --git a/docs/examples/databases/delete-attribute.md b/docs/examples/databases/delete-attribute.md index ceda5de2..f3ba6476 100644 --- a/docs/examples/databases/delete-attribute.md +++ b/docs/examples/databases/delete-attribute.md @@ -12,6 +12,6 @@ databases = Databases(client) result = databases.delete_attribute( database_id = '', collection_id = '', - key = '' + key = '' ) ``` diff --git a/docs/examples/databases/delete-index.md b/docs/examples/databases/delete-index.md index 62fa4875..1e48fa8e 100644 --- a/docs/examples/databases/delete-index.md +++ b/docs/examples/databases/delete-index.md @@ -12,6 +12,6 @@ databases = Databases(client) result = databases.delete_index( database_id = '', collection_id = '', - key = '' + key = '' ) ``` diff --git a/docs/examples/databases/get-attribute.md b/docs/examples/databases/get-attribute.md index d841226f..880a5872 100644 --- a/docs/examples/databases/get-attribute.md +++ b/docs/examples/databases/get-attribute.md @@ -23,7 +23,7 @@ databases = Databases(client) result: Union[AttributeBoolean, AttributeInteger, AttributeFloat, AttributeEmail, AttributeEnum, AttributeUrl, AttributeIp, AttributeDatetime, AttributeRelationship, AttributeString] = databases.get_attribute( database_id = '', collection_id = '', - key = '' + key = '' ) print(result.model_dump()) diff --git a/docs/examples/databases/get-index.md b/docs/examples/databases/get-index.md index d76008ac..4d327be1 100644 --- a/docs/examples/databases/get-index.md +++ b/docs/examples/databases/get-index.md @@ -13,7 +13,7 @@ databases = Databases(client) result: Index = databases.get_index( database_id = '', collection_id = '', - key = '' + key = '' ) print(result.model_dump()) diff --git a/docs/examples/databases/increment-document-attribute.md b/docs/examples/databases/increment-document-attribute.md index 37fb1244..77a96bd3 100644 --- a/docs/examples/databases/increment-document-attribute.md +++ b/docs/examples/databases/increment-document-attribute.md @@ -14,9 +14,9 @@ result: Document = databases.increment_document_attribute( database_id = '', collection_id = '', document_id = '', - attribute = '', - value = None, # optional - max = None, # optional + attribute = '', + value = 1, # optional + max = 100, # optional transaction_id = '' # optional ) diff --git a/docs/examples/databases/update-big-int-attribute.md b/docs/examples/databases/update-big-int-attribute.md index 35c0c14c..84ecb942 100644 --- a/docs/examples/databases/update-big-int-attribute.md +++ b/docs/examples/databases/update-big-int-attribute.md @@ -13,12 +13,12 @@ databases = Databases(client) result: AttributeBigint = databases.update_big_int_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 0, + min = 0, # optional + max = 1000000, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-boolean-attribute.md b/docs/examples/databases/update-boolean-attribute.md index 34ae961c..26ac8023 100644 --- a/docs/examples/databases/update-boolean-attribute.md +++ b/docs/examples/databases/update-boolean-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeBoolean = databases.update_boolean_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = False, - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-datetime-attribute.md b/docs/examples/databases/update-datetime-attribute.md index 0c585a8e..cf80c1d7 100644 --- a/docs/examples/databases/update-datetime-attribute.md +++ b/docs/examples/databases/update-datetime-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeDatetime = databases.update_datetime_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = '2020-10-15T06:38:00.000+00:00', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-email-attribute.md b/docs/examples/databases/update-email-attribute.md index ac6bb193..6a6b2d52 100644 --- a/docs/examples/databases/update-email-attribute.md +++ b/docs/examples/databases/update-email-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeEmail = databases.update_email_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = 'email@example.com', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-enum-attribute.md b/docs/examples/databases/update-enum-attribute.md index d7cf1fe9..822f712c 100644 --- a/docs/examples/databases/update-enum-attribute.md +++ b/docs/examples/databases/update-enum-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeEnum = databases.update_enum_attribute( database_id = '', collection_id = '', - key = '', - elements = [], + key = '', + elements = ["active", "inactive"], required = False, - default = '', - new_key = '' # optional + default = 'active', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-float-attribute.md b/docs/examples/databases/update-float-attribute.md index c1182556..4497a4a5 100644 --- a/docs/examples/databases/update-float-attribute.md +++ b/docs/examples/databases/update-float-attribute.md @@ -13,12 +13,12 @@ databases = Databases(client) result: AttributeFloat = databases.update_float_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 10.5, + min = 0, # optional + max = 100, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-integer-attribute.md b/docs/examples/databases/update-integer-attribute.md index ddeebf4f..61fe8bcc 100644 --- a/docs/examples/databases/update-integer-attribute.md +++ b/docs/examples/databases/update-integer-attribute.md @@ -13,12 +13,12 @@ databases = Databases(client) result: AttributeInteger = databases.update_integer_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 10, + min = 0, # optional + max = 100, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-ip-attribute.md b/docs/examples/databases/update-ip-attribute.md index 11978eb0..89945ee3 100644 --- a/docs/examples/databases/update-ip-attribute.md +++ b/docs/examples/databases/update-ip-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeIp = databases.update_ip_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = '192.0.2.0', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-line-attribute.md b/docs/examples/databases/update-line-attribute.md index ba823763..96d6b4e6 100644 --- a/docs/examples/databases/update-line-attribute.md +++ b/docs/examples/databases/update-line-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeLine = databases.update_line_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [[1, 2], [3, 4], [5, 6]], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-longtext-attribute.md b/docs/examples/databases/update-longtext-attribute.md index ec7050e7..d039a6e0 100644 --- a/docs/examples/databases/update-longtext-attribute.md +++ b/docs/examples/databases/update-longtext-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeLongtext = databases.update_longtext_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-mediumtext-attribute.md b/docs/examples/databases/update-mediumtext-attribute.md index 1036a808..dc960fc6 100644 --- a/docs/examples/databases/update-mediumtext-attribute.md +++ b/docs/examples/databases/update-mediumtext-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeMediumtext = databases.update_mediumtext_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-point-attribute.md b/docs/examples/databases/update-point-attribute.md index 9095bdf6..bf6a94d8 100644 --- a/docs/examples/databases/update-point-attribute.md +++ b/docs/examples/databases/update-point-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributePoint = databases.update_point_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [1, 2], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-polygon-attribute.md b/docs/examples/databases/update-polygon-attribute.md index dffcaa57..2dd1194c 100644 --- a/docs/examples/databases/update-polygon-attribute.md +++ b/docs/examples/databases/update-polygon-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributePolygon = databases.update_polygon_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = [[[1, 2], [3, 4], [5, 6], [1, 2]]], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-relationship-attribute.md b/docs/examples/databases/update-relationship-attribute.md index 226e8b0a..a507aca1 100644 --- a/docs/examples/databases/update-relationship-attribute.md +++ b/docs/examples/databases/update-relationship-attribute.md @@ -14,9 +14,9 @@ databases = Databases(client) result: AttributeRelationship = databases.update_relationship_attribute( database_id = '', collection_id = '', - key = '', + key = '', on_delete = RelationMutate.CASCADE, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-string-attribute.md b/docs/examples/databases/update-string-attribute.md index 897a3134..bfe14df1 100644 --- a/docs/examples/databases/update-string-attribute.md +++ b/docs/examples/databases/update-string-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeString = databases.update_string_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', + default = 'Hello World', size = 1, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-text-attribute.md b/docs/examples/databases/update-text-attribute.md index 02b5fd35..01f66d13 100644 --- a/docs/examples/databases/update-text-attribute.md +++ b/docs/examples/databases/update-text-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeText = databases.update_text_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-url-attribute.md b/docs/examples/databases/update-url-attribute.md index d5747708..9f05a4a4 100644 --- a/docs/examples/databases/update-url-attribute.md +++ b/docs/examples/databases/update-url-attribute.md @@ -13,10 +13,10 @@ databases = Databases(client) result: AttributeUrl = databases.update_url_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, default = 'https://example.com', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/databases/update-varchar-attribute.md b/docs/examples/databases/update-varchar-attribute.md index f3079e16..b844a712 100644 --- a/docs/examples/databases/update-varchar-attribute.md +++ b/docs/examples/databases/update-varchar-attribute.md @@ -13,11 +13,11 @@ databases = Databases(client) result: AttributeVarchar = databases.update_varchar_attribute( database_id = '', collection_id = '', - key = '', + key = '', required = False, - default = '', + default = 'Hello World', size = 1, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/documentsdb/create-collection.md b/docs/examples/documentsdb/create-collection.md new file mode 100644 index 00000000..b717460f --- /dev/null +++ b/docs/examples/documentsdb/create-collection.md @@ -0,0 +1,27 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Collection +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Collection = documents_db.create_collection( + database_id = '', + collection_id = '', + name = '', + permissions = [Permission.read(Role.any())], # optional + document_security = False, # optional + enabled = False, # optional + attributes = [], # optional + indexes = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-document.md b/docs/examples/documentsdb/create-document.md new file mode 100644 index 00000000..1fa38033 --- /dev/null +++ b/docs/examples/documentsdb/create-document.md @@ -0,0 +1,30 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.create_document( + database_id = '', + collection_id = '', + document_id = '', + data = { + "username": "walter.obrien", + "email": "walter.obrien@example.com", + "fullName": "Walter O'Brien", + "age": 30, + "isAdmin": False + }, + permissions = [Permission.read(Role.any())] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-documents.md b/docs/examples/documentsdb/create-documents.md new file mode 100644 index 00000000..661c32dd --- /dev/null +++ b/docs/examples/documentsdb/create-documents.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: DocumentList = documents_db.create_documents( + database_id = '', + collection_id = '', + documents = [] +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-failover.md b/docs/examples/documentsdb/create-failover.md new file mode 100644 index 00000000..fc7b0570 --- /dev/null +++ b/docs/examples/documentsdb/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DedicatedDatabase = documents_db.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-index.md b/docs/examples/documentsdb/create-index.md new file mode 100644 index 00000000..34a36dc8 --- /dev/null +++ b/docs/examples/documentsdb/create-index.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Index +from appwrite.enums import DocumentsDBIndexType +from appwrite.enums import OrderBy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Index = documents_db.create_index( + database_id = '', + collection_id = '', + key = '', + type = DocumentsDBIndexType.KEY, + attributes = [], + orders = [OrderBy.ASC], # optional + lengths = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-operations.md b/docs/examples/documentsdb/create-operations.md new file mode 100644 index 00000000..23128e81 --- /dev/null +++ b/docs/examples/documentsdb/create-operations.md @@ -0,0 +1,29 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Transaction = documents_db.create_operations( + transaction_id = '', + operations = [ + { + "action": "create", + "databaseId": "", + "collectionId": "", + "documentId": "", + "data": { + "name": "Walter O'Brien" + } + } + ] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create-transaction.md b/docs/examples/documentsdb/create-transaction.md new file mode 100644 index 00000000..d34b358e --- /dev/null +++ b/docs/examples/documentsdb/create-transaction.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Transaction = documents_db.create_transaction( + ttl = 60 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/create.md b/docs/examples/documentsdb/create.md new file mode 100644 index 00000000..b8da9d4b --- /dev/null +++ b/docs/examples/documentsdb/create.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Database = documents_db.create( + database_id = '', + name = '', + enabled = False, # optional + specification = 'serverless', # optional + replicas = 0, # optional + sync_mode = 'async' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/decrement-document-attribute.md b/docs/examples/documentsdb/decrement-document-attribute.md new file mode 100644 index 00000000..d6c75329 --- /dev/null +++ b/docs/examples/documentsdb/decrement-document-attribute.md @@ -0,0 +1,24 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.decrement_document_attribute( + database_id = '', + collection_id = '', + document_id = '', + attribute = '', + value = 1, # optional + min = 0, # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/delete-collection.md b/docs/examples/documentsdb/delete-collection.md new file mode 100644 index 00000000..1652ab2b --- /dev/null +++ b/docs/examples/documentsdb/delete-collection.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result = documents_db.delete_collection( + database_id = '', + collection_id = '' +) +``` diff --git a/docs/examples/documentsdb/delete-document.md b/docs/examples/documentsdb/delete-document.md new file mode 100644 index 00000000..e588088e --- /dev/null +++ b/docs/examples/documentsdb/delete-document.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result = documents_db.delete_document( + database_id = '', + collection_id = '', + document_id = '', + transaction_id = '' # optional +) +``` diff --git a/docs/examples/documentsdb/delete-documents.md b/docs/examples/documentsdb/delete-documents.md new file mode 100644 index 00000000..8bc343de --- /dev/null +++ b/docs/examples/documentsdb/delete-documents.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DocumentList = documents_db.delete_documents( + database_id = '', + collection_id = '', + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/delete-index.md b/docs/examples/documentsdb/delete-index.md new file mode 100644 index 00000000..befd9fee --- /dev/null +++ b/docs/examples/documentsdb/delete-index.md @@ -0,0 +1,17 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result = documents_db.delete_index( + database_id = '', + collection_id = '', + key = '' +) +``` diff --git a/docs/examples/documentsdb/delete-transaction.md b/docs/examples/documentsdb/delete-transaction.md new file mode 100644 index 00000000..009bf807 --- /dev/null +++ b/docs/examples/documentsdb/delete-transaction.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result = documents_db.delete_transaction( + transaction_id = '' +) +``` diff --git a/docs/examples/documentsdb/delete.md b/docs/examples/documentsdb/delete.md new file mode 100644 index 00000000..64845091 --- /dev/null +++ b/docs/examples/documentsdb/delete.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result = documents_db.delete( + database_id = '' +) +``` diff --git a/docs/examples/documentsdb/get-collection.md b/docs/examples/documentsdb/get-collection.md new file mode 100644 index 00000000..5ec739b8 --- /dev/null +++ b/docs/examples/documentsdb/get-collection.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Collection + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Collection = documents_db.get_collection( + database_id = '', + collection_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get-document.md b/docs/examples/documentsdb/get-document.md new file mode 100644 index 00000000..3f0006e7 --- /dev/null +++ b/docs/examples/documentsdb/get-document.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.get_document( + database_id = '', + collection_id = '', + document_id = '', + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get-index.md b/docs/examples/documentsdb/get-index.md new file mode 100644 index 00000000..598873f0 --- /dev/null +++ b/docs/examples/documentsdb/get-index.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Index + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Index = documents_db.get_index( + database_id = '', + collection_id = '', + key = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get-replicas.md b/docs/examples/documentsdb/get-replicas.md new file mode 100644 index 00000000..1eabb127 --- /dev/null +++ b/docs/examples/documentsdb/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DedicatedDatabaseReplicas = documents_db.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get-status.md b/docs/examples/documentsdb/get-status.md new file mode 100644 index 00000000..9e26368a --- /dev/null +++ b/docs/examples/documentsdb/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DatabaseStatus = documents_db.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get-transaction.md b/docs/examples/documentsdb/get-transaction.md new file mode 100644 index 00000000..27d88ee7 --- /dev/null +++ b/docs/examples/documentsdb/get-transaction.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Transaction = documents_db.get_transaction( + transaction_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/get.md b/docs/examples/documentsdb/get.md new file mode 100644 index 00000000..fc2ffb9b --- /dev/null +++ b/docs/examples/documentsdb/get.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Database = documents_db.get( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/increment-document-attribute.md b/docs/examples/documentsdb/increment-document-attribute.md new file mode 100644 index 00000000..08e61883 --- /dev/null +++ b/docs/examples/documentsdb/increment-document-attribute.md @@ -0,0 +1,24 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.increment_document_attribute( + database_id = '', + collection_id = '', + document_id = '', + attribute = '', + value = 1, # optional + max = 100, # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-collections.md b/docs/examples/documentsdb/list-collections.md new file mode 100644 index 00000000..0d72a376 --- /dev/null +++ b/docs/examples/documentsdb/list-collections.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import CollectionList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: CollectionList = documents_db.list_collections( + database_id = '', + queries = [], # optional + search = '', # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-documents.md b/docs/examples/documentsdb/list-documents.md new file mode 100644 index 00000000..c1b2a360 --- /dev/null +++ b/docs/examples/documentsdb/list-documents.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: DocumentList = documents_db.list_documents( + database_id = '', + collection_id = '', + queries = [], # optional + transaction_id = '', # optional + total = False, # optional + ttl = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-indexes.md b/docs/examples/documentsdb/list-indexes.md new file mode 100644 index 00000000..26655d72 --- /dev/null +++ b/docs/examples/documentsdb/list-indexes.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import IndexList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: IndexList = documents_db.list_indexes( + database_id = '', + collection_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-operations.md b/docs/examples/documentsdb/list-operations.md new file mode 100644 index 00000000..90c01baa --- /dev/null +++ b/docs/examples/documentsdb/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DedicatedDatabaseOperationList = documents_db.list_operations( + database_id = '', + status = 'queued', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-specifications.md b/docs/examples/documentsdb/list-specifications.md new file mode 100644 index 00000000..6917c483 --- /dev/null +++ b/docs/examples/documentsdb/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DedicatedDatabaseSpecificationList = documents_db.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list-transactions.md b/docs/examples/documentsdb/list-transactions.md new file mode 100644 index 00000000..6dc7aae2 --- /dev/null +++ b/docs/examples/documentsdb/list-transactions.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import TransactionList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: TransactionList = documents_db.list_transactions( + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/list.md b/docs/examples/documentsdb/list.md new file mode 100644 index 00000000..59d3557e --- /dev/null +++ b/docs/examples/documentsdb/list.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DatabaseList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DatabaseList = documents_db.list( + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/update-collection.md b/docs/examples/documentsdb/update-collection.md new file mode 100644 index 00000000..955fb28f --- /dev/null +++ b/docs/examples/documentsdb/update-collection.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Collection +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Collection = documents_db.update_collection( + database_id = '', + collection_id = '', + name = '', + permissions = [Permission.read(Role.any())], # optional + document_security = False, # optional + enabled = False, # optional + purge = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/update-document.md b/docs/examples/documentsdb/update-document.md new file mode 100644 index 00000000..cf0bfcc9 --- /dev/null +++ b/docs/examples/documentsdb/update-document.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.update_document( + database_id = '', + collection_id = '', + document_id = '', + data = {}, # optional + permissions = [Permission.read(Role.any())], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/update-documents.md b/docs/examples/documentsdb/update-documents.md new file mode 100644 index 00000000..2c183e55 --- /dev/null +++ b/docs/examples/documentsdb/update-documents.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DocumentList = documents_db.update_documents( + database_id = '', + collection_id = '', + data = {}, # optional + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/update-transaction.md b/docs/examples/documentsdb/update-transaction.md new file mode 100644 index 00000000..fff946cb --- /dev/null +++ b/docs/examples/documentsdb/update-transaction.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Transaction = documents_db.update_transaction( + transaction_id = '', + commit = False, # optional + rollback = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/update.md b/docs/examples/documentsdb/update.md new file mode 100644 index 00000000..03d7e861 --- /dev/null +++ b/docs/examples/documentsdb/update.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: Database = documents_db.update( + database_id = '', + name = '', + enabled = False, # optional + specification = 'serverless', # optional + replicas = 0, # optional + sync_mode = 'async' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/upsert-document.md b/docs/examples/documentsdb/upsert-document.md new file mode 100644 index 00000000..07086f4a --- /dev/null +++ b/docs/examples/documentsdb/upsert-document.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +documents_db = DocumentsDB(client) + +result: Document = documents_db.upsert_document( + database_id = '', + collection_id = '', + document_id = '', + data = {}, # optional + permissions = [Permission.read(Role.any())], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/documentsdb/upsert-documents.md b/docs/examples/documentsdb/upsert-documents.md new file mode 100644 index 00000000..d98b227c --- /dev/null +++ b/docs/examples/documentsdb/upsert-documents.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.documents_db import DocumentsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +documents_db = DocumentsDB(client) + +result: DocumentList = documents_db.upsert_documents( + database_id = '', + collection_id = '', + documents = [], + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/functions/create.md b/docs/examples/functions/create.md index 1c6c3854..e3520485 100644 --- a/docs/examples/functions/create.md +++ b/docs/examples/functions/create.md @@ -18,7 +18,7 @@ result: Function = functions.create( runtime = Runtime.NODE_14_5, execute = ["any"], # optional events = [], # optional - schedule = '', # optional + schedule = '0 0 * * *', # optional timeout = 1, # optional enabled = False, # optional logging = False, # optional @@ -32,8 +32,8 @@ result: Function = functions.create( provider_root_directory = '', # optional provider_branches = [], # optional provider_paths = [], # optional - build_specification = '', # optional - runtime_specification = '', # optional + build_specification = 's-1vcpu-512mb', # optional + runtime_specification = 's-1vcpu-512mb', # optional deployment_retention = 0 # optional ) diff --git a/docs/examples/functions/update.md b/docs/examples/functions/update.md index c7b1393a..d7dd50df 100644 --- a/docs/examples/functions/update.md +++ b/docs/examples/functions/update.md @@ -18,7 +18,7 @@ result: Function = functions.update( runtime = Runtime.NODE_14_5, # optional execute = ["any"], # optional events = [], # optional - schedule = '', # optional + schedule = '0 0 * * *', # optional timeout = 1, # optional enabled = False, # optional logging = False, # optional @@ -32,8 +32,8 @@ result: Function = functions.update( provider_root_directory = '', # optional provider_branches = [], # optional provider_paths = [], # optional - build_specification = '', # optional - runtime_specification = '', # optional + build_specification = 's-1vcpu-512mb', # optional + runtime_specification = 's-1vcpu-512mb', # optional deployment_retention = 0 # optional ) diff --git a/docs/examples/messaging/create-mailgun-provider.md b/docs/examples/messaging/create-mailgun-provider.md index d16f453a..89ecea10 100644 --- a/docs/examples/messaging/create-mailgun-provider.md +++ b/docs/examples/messaging/create-mailgun-provider.md @@ -14,7 +14,7 @@ result: Provider = messaging.create_mailgun_provider( provider_id = '', name = '', api_key = '', # optional - domain = '', # optional + domain = 'example.com', # optional is_eu_region = False, # optional from_name = '', # optional from_email = 'email@example.com', # optional diff --git a/docs/examples/messaging/create-push.md b/docs/examples/messaging/create-push.md index 81a15dab..155128a0 100644 --- a/docs/examples/messaging/create-push.md +++ b/docs/examples/messaging/create-push.md @@ -25,7 +25,7 @@ result: Message = messaging.create_push( sound = '', # optional color = '', # optional tag = '', # optional - badge = None, # optional + badge = 1, # optional draft = False, # optional scheduled_at = '2020-10-15T06:38:00.000+00:00', # optional content_available = False, # optional diff --git a/docs/examples/messaging/create-smtp-provider.md b/docs/examples/messaging/create-smtp-provider.md index fd5995f2..9681bc18 100644 --- a/docs/examples/messaging/create-smtp-provider.md +++ b/docs/examples/messaging/create-smtp-provider.md @@ -15,7 +15,7 @@ result: Provider = messaging.create_smtp_provider( provider_id = '', name = '', host = '', - port = 1, # optional + port = 587, # optional username = '', # optional password = 'password', # optional encryption = SmtpEncryption.NONE, # optional diff --git a/docs/examples/messaging/update-mailgun-provider.md b/docs/examples/messaging/update-mailgun-provider.md index 5c3285cd..82086c41 100644 --- a/docs/examples/messaging/update-mailgun-provider.md +++ b/docs/examples/messaging/update-mailgun-provider.md @@ -14,7 +14,7 @@ result: Provider = messaging.update_mailgun_provider( provider_id = '', name = '', # optional api_key = '', # optional - domain = '', # optional + domain = 'example.com', # optional is_eu_region = False, # optional enabled = False, # optional from_name = '', # optional diff --git a/docs/examples/messaging/update-push.md b/docs/examples/messaging/update-push.md index 913de5a1..0c592d6c 100644 --- a/docs/examples/messaging/update-push.md +++ b/docs/examples/messaging/update-push.md @@ -25,7 +25,7 @@ result: Message = messaging.update_push( sound = '', # optional color = '', # optional tag = '', # optional - badge = None, # optional + badge = 1, # optional draft = False, # optional scheduled_at = '2020-10-15T06:38:00.000+00:00', # optional content_available = False, # optional diff --git a/docs/examples/mongo/create-backup-policy.md b/docs/examples/mongo/create-backup-policy.md new file mode 100644 index 00000000..08db4ded --- /dev/null +++ b/docs/examples/mongo/create-backup-policy.md @@ -0,0 +1,24 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: BackupPolicy = mongo.create_backup_policy( + database_id = '', + policy_id = '', + name = '', + schedule = '', + retention = 1, + type = 'full', # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-backup.md b/docs/examples/mongo/create-backup.md new file mode 100644 index 00000000..713de58c --- /dev/null +++ b/docs/examples/mongo/create-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseBackup = mongo.create_backup( + database_id = '', + type = 'full' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-branch.md b/docs/examples/mongo/create-branch.md new file mode 100644 index 00000000..9d8f6384 --- /dev/null +++ b/docs/examples/mongo/create-branch.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.create_branch( + database_id = '', + branch_id = '', # optional + ttl = 300 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-failover.md b/docs/examples/mongo/create-failover.md new file mode 100644 index 00000000..09b08d1a --- /dev/null +++ b/docs/examples/mongo/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-migration.md b/docs/examples/mongo/create-migration.md new file mode 100644 index 00000000..d8f75db1 --- /dev/null +++ b/docs/examples/mongo/create-migration.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.create_migration( + database_id = '', + target_type = 'shared', + specification = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-restoration.md b/docs/examples/mongo/create-restoration.md new file mode 100644 index 00000000..0ba9b82f --- /dev/null +++ b/docs/examples/mongo/create-restoration.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseRestoration = mongo.create_restoration( + database_id = '', + type = 'backup', # optional + backup_id = '', # optional + target_database_id = '', # optional + target_time = '2020-10-15T06:38:00.000+00:00' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create-upgrade.md b/docs/examples/mongo/create-upgrade.md new file mode 100644 index 00000000..111bea18 --- /dev/null +++ b/docs/examples/mongo/create-upgrade.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.create_upgrade( + database_id = '', + target_version = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/create.md b/docs/examples/mongo/create.md new file mode 100644 index 00000000..9909aa62 --- /dev/null +++ b/docs/examples/mongo/create.md @@ -0,0 +1,31 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.create( + database_id = '', + name = '', + version = '17', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/delete-backup-policy.md b/docs/examples/mongo/delete-backup-policy.md new file mode 100644 index 00000000..f5a65754 --- /dev/null +++ b/docs/examples/mongo/delete-backup-policy.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result = mongo.delete_backup_policy( + database_id = '', + policy_id = '' +) +``` diff --git a/docs/examples/mongo/delete-backup.md b/docs/examples/mongo/delete-backup.md new file mode 100644 index 00000000..bbcd78c4 --- /dev/null +++ b/docs/examples/mongo/delete-backup.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result = mongo.delete_backup( + database_id = '', + backup_id = '' +) +``` diff --git a/docs/examples/mongo/delete-branch.md b/docs/examples/mongo/delete-branch.md new file mode 100644 index 00000000..879ef438 --- /dev/null +++ b/docs/examples/mongo/delete-branch.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.delete_branch( + database_id = '', + branch_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/delete.md b/docs/examples/mongo/delete.md new file mode 100644 index 00000000..9ba0e46c --- /dev/null +++ b/docs/examples/mongo/delete.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result = mongo.delete( + database_id = '' +) +``` diff --git a/docs/examples/mongo/get-backup-policy.md b/docs/examples/mongo/get-backup-policy.md new file mode 100644 index 00000000..1fb3406b --- /dev/null +++ b/docs/examples/mongo/get-backup-policy.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: BackupPolicy = mongo.get_backup_policy( + database_id = '', + policy_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get-backup.md b/docs/examples/mongo/get-backup.md new file mode 100644 index 00000000..49e7db89 --- /dev/null +++ b/docs/examples/mongo/get-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseBackup = mongo.get_backup( + database_id = '', + backup_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get-pitr.md b/docs/examples/mongo/get-pitr.md new file mode 100644 index 00000000..b3ae9b81 --- /dev/null +++ b/docs/examples/mongo/get-pitr.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabasePITRWindows + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabasePITRWindows = mongo.get_pitr( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get-replicas.md b/docs/examples/mongo/get-replicas.md new file mode 100644 index 00000000..2f8786ed --- /dev/null +++ b/docs/examples/mongo/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseReplicas = mongo.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get-restoration.md b/docs/examples/mongo/get-restoration.md new file mode 100644 index 00000000..7e257259 --- /dev/null +++ b/docs/examples/mongo/get-restoration.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseRestoration = mongo.get_restoration( + database_id = '', + restoration_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get-status.md b/docs/examples/mongo/get-status.md new file mode 100644 index 00000000..f2f832dd --- /dev/null +++ b/docs/examples/mongo/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DatabaseStatus = mongo.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/get.md b/docs/examples/mongo/get.md new file mode 100644 index 00000000..c89e66a5 --- /dev/null +++ b/docs/examples/mongo/get.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.get( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-backup-policies.md b/docs/examples/mongo/list-backup-policies.md new file mode 100644 index 00000000..c023cc1d --- /dev/null +++ b/docs/examples/mongo/list-backup-policies.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import BackupPolicyList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: BackupPolicyList = mongo.list_backup_policies( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-backups.md b/docs/examples/mongo/list-backups.md new file mode 100644 index 00000000..bf896520 --- /dev/null +++ b/docs/examples/mongo/list-backups.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseBackupList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseBackupList = mongo.list_backups( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-branches.md b/docs/examples/mongo/list-branches.md new file mode 100644 index 00000000..4c1f1a4e --- /dev/null +++ b/docs/examples/mongo/list-branches.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseBranchList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseBranchList = mongo.list_branches( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-operations.md b/docs/examples/mongo/list-operations.md new file mode 100644 index 00000000..9c2f77a2 --- /dev/null +++ b/docs/examples/mongo/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseOperationList = mongo.list_operations( + database_id = '', + status = 'queued', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-restorations.md b/docs/examples/mongo/list-restorations.md new file mode 100644 index 00000000..89bb120e --- /dev/null +++ b/docs/examples/mongo/list-restorations.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseRestorationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseRestorationList = mongo.list_restorations( + database_id = '', + status = 'pending', # optional + type = 'backup', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list-specifications.md b/docs/examples/mongo/list-specifications.md new file mode 100644 index 00000000..6828191e --- /dev/null +++ b/docs/examples/mongo/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseSpecificationList = mongo.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/list.md b/docs/examples/mongo/list.md new file mode 100644 index 00000000..b956cebe --- /dev/null +++ b/docs/examples/mongo/list.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseList = mongo.list( + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/update-backup-policy.md b/docs/examples/mongo/update-backup-policy.md new file mode 100644 index 00000000..5a02ffe1 --- /dev/null +++ b/docs/examples/mongo/update-backup-policy.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: BackupPolicy = mongo.update_backup_policy( + database_id = '', + policy_id = '', + name = '', # optional + schedule = '', # optional + retention = 1, # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/update-backup-storage.md b/docs/examples/mongo/update-backup-storage.md new file mode 100644 index 00000000..9a62d4fd --- /dev/null +++ b/docs/examples/mongo/update-backup-storage.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabaseBackupStorage + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabaseBackupStorage = mongo.update_backup_storage( + database_id = '', + provider = 's3', + bucket = '', + access_key = '', + secret_key = '', + region = '', # optional + prefix = '', # optional + endpoint = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/update-credentials.md b/docs/examples/mongo/update-credentials.md new file mode 100644 index 00000000..e3dea54f --- /dev/null +++ b/docs/examples/mongo/update-credentials.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.update_credentials( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/update-maintenance.md b/docs/examples/mongo/update-maintenance.md new file mode 100644 index 00000000..081016ab --- /dev/null +++ b/docs/examples/mongo/update-maintenance.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.update_maintenance( + database_id = '', + day = 'sun', + hour_utc = 0 +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mongo/update.md b/docs/examples/mongo/update.md new file mode 100644 index 00000000..e14bffc7 --- /dev/null +++ b/docs/examples/mongo/update.md @@ -0,0 +1,38 @@ +```python +from appwrite.client import Client +from appwrite.services.mongo import Mongo +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mongo = Mongo(client) + +result: DedicatedDatabase = mongo.update( + database_id = '', + name = '', # optional + status = 'ready', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0, # optional + metrics_trace_sample_rate = None, # optional + metrics_slow_query_log_threshold_ms = 0, # optional + sql_api_enabled = False, # optional + sql_api_allowed_statements = [], # optional + sql_api_max_rows = 1, # optional + sql_api_max_bytes = 1024, # optional + sql_api_timeout_seconds = 1 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-backup-policy.md b/docs/examples/mysql/create-backup-policy.md new file mode 100644 index 00000000..bb76383a --- /dev/null +++ b/docs/examples/mysql/create-backup-policy.md @@ -0,0 +1,24 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: BackupPolicy = mysql.create_backup_policy( + database_id = '', + policy_id = '', + name = '', + schedule = '', + retention = 1, + type = 'full', # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-backup.md b/docs/examples/mysql/create-backup.md new file mode 100644 index 00000000..05e98dd4 --- /dev/null +++ b/docs/examples/mysql/create-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseBackup = mysql.create_backup( + database_id = '', + type = 'full' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-branch.md b/docs/examples/mysql/create-branch.md new file mode 100644 index 00000000..aec24a08 --- /dev/null +++ b/docs/examples/mysql/create-branch.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.create_branch( + database_id = '', + branch_id = '', # optional + ttl = 300 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-execution.md b/docs/examples/mysql/create-execution.md new file mode 100644 index 00000000..e4cd9772 --- /dev/null +++ b/docs/examples/mysql/create-execution.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseExecution + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseExecution = mysql.create_execution( + database_id = '', + sql = '', + bindings = {}, # optional + timeout_seconds = 1 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-failover.md b/docs/examples/mysql/create-failover.md new file mode 100644 index 00000000..cde13f40 --- /dev/null +++ b/docs/examples/mysql/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-migration.md b/docs/examples/mysql/create-migration.md new file mode 100644 index 00000000..b5616780 --- /dev/null +++ b/docs/examples/mysql/create-migration.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.create_migration( + database_id = '', + target_type = 'shared', + specification = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-restoration.md b/docs/examples/mysql/create-restoration.md new file mode 100644 index 00000000..0c3481f6 --- /dev/null +++ b/docs/examples/mysql/create-restoration.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseRestoration = mysql.create_restoration( + database_id = '', + type = 'backup', # optional + backup_id = '', # optional + target_database_id = '', # optional + target_time = '2020-10-15T06:38:00.000+00:00' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create-upgrade.md b/docs/examples/mysql/create-upgrade.md new file mode 100644 index 00000000..f1e246ef --- /dev/null +++ b/docs/examples/mysql/create-upgrade.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.create_upgrade( + database_id = '', + target_version = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/create.md b/docs/examples/mysql/create.md new file mode 100644 index 00000000..92a7c007 --- /dev/null +++ b/docs/examples/mysql/create.md @@ -0,0 +1,31 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.create( + database_id = '', + name = '', + version = '17', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/delete-backup-policy.md b/docs/examples/mysql/delete-backup-policy.md new file mode 100644 index 00000000..7f6fbf88 --- /dev/null +++ b/docs/examples/mysql/delete-backup-policy.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result = mysql.delete_backup_policy( + database_id = '', + policy_id = '' +) +``` diff --git a/docs/examples/mysql/delete-backup.md b/docs/examples/mysql/delete-backup.md new file mode 100644 index 00000000..cd0f7322 --- /dev/null +++ b/docs/examples/mysql/delete-backup.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result = mysql.delete_backup( + database_id = '', + backup_id = '' +) +``` diff --git a/docs/examples/mysql/delete-branch.md b/docs/examples/mysql/delete-branch.md new file mode 100644 index 00000000..7e7bbbdc --- /dev/null +++ b/docs/examples/mysql/delete-branch.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.delete_branch( + database_id = '', + branch_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/delete.md b/docs/examples/mysql/delete.md new file mode 100644 index 00000000..9632ba06 --- /dev/null +++ b/docs/examples/mysql/delete.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result = mysql.delete( + database_id = '' +) +``` diff --git a/docs/examples/mysql/get-backup-policy.md b/docs/examples/mysql/get-backup-policy.md new file mode 100644 index 00000000..0d3baec5 --- /dev/null +++ b/docs/examples/mysql/get-backup-policy.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: BackupPolicy = mysql.get_backup_policy( + database_id = '', + policy_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-backup.md b/docs/examples/mysql/get-backup.md new file mode 100644 index 00000000..eb782c5e --- /dev/null +++ b/docs/examples/mysql/get-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseBackup = mysql.get_backup( + database_id = '', + backup_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-pitr.md b/docs/examples/mysql/get-pitr.md new file mode 100644 index 00000000..5202ed66 --- /dev/null +++ b/docs/examples/mysql/get-pitr.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabasePITRWindows + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabasePITRWindows = mysql.get_pitr( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-pooler.md b/docs/examples/mysql/get-pooler.md new file mode 100644 index 00000000..fc2af012 --- /dev/null +++ b/docs/examples/mysql/get-pooler.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabasePooler + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabasePooler = mysql.get_pooler( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-replicas.md b/docs/examples/mysql/get-replicas.md new file mode 100644 index 00000000..a35bf822 --- /dev/null +++ b/docs/examples/mysql/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseReplicas = mysql.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-restoration.md b/docs/examples/mysql/get-restoration.md new file mode 100644 index 00000000..0e760273 --- /dev/null +++ b/docs/examples/mysql/get-restoration.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseRestoration = mysql.get_restoration( + database_id = '', + restoration_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get-status.md b/docs/examples/mysql/get-status.md new file mode 100644 index 00000000..97adbe6c --- /dev/null +++ b/docs/examples/mysql/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DatabaseStatus = mysql.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/get.md b/docs/examples/mysql/get.md new file mode 100644 index 00000000..431c72ca --- /dev/null +++ b/docs/examples/mysql/get.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.get( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-backup-policies.md b/docs/examples/mysql/list-backup-policies.md new file mode 100644 index 00000000..0b5328d4 --- /dev/null +++ b/docs/examples/mysql/list-backup-policies.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import BackupPolicyList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: BackupPolicyList = mysql.list_backup_policies( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-backups.md b/docs/examples/mysql/list-backups.md new file mode 100644 index 00000000..5a533951 --- /dev/null +++ b/docs/examples/mysql/list-backups.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseBackupList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseBackupList = mysql.list_backups( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-branches.md b/docs/examples/mysql/list-branches.md new file mode 100644 index 00000000..6c05f543 --- /dev/null +++ b/docs/examples/mysql/list-branches.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseBranchList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseBranchList = mysql.list_branches( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-operations.md b/docs/examples/mysql/list-operations.md new file mode 100644 index 00000000..1b4d3c97 --- /dev/null +++ b/docs/examples/mysql/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseOperationList = mysql.list_operations( + database_id = '', + status = 'queued', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-restorations.md b/docs/examples/mysql/list-restorations.md new file mode 100644 index 00000000..efe346da --- /dev/null +++ b/docs/examples/mysql/list-restorations.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseRestorationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseRestorationList = mysql.list_restorations( + database_id = '', + status = 'pending', # optional + type = 'backup', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list-specifications.md b/docs/examples/mysql/list-specifications.md new file mode 100644 index 00000000..c5d48d5a --- /dev/null +++ b/docs/examples/mysql/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseSpecificationList = mysql.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/list.md b/docs/examples/mysql/list.md new file mode 100644 index 00000000..865e474f --- /dev/null +++ b/docs/examples/mysql/list.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseList = mysql.list( + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update-backup-policy.md b/docs/examples/mysql/update-backup-policy.md new file mode 100644 index 00000000..65f9a9a3 --- /dev/null +++ b/docs/examples/mysql/update-backup-policy.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: BackupPolicy = mysql.update_backup_policy( + database_id = '', + policy_id = '', + name = '', # optional + schedule = '', # optional + retention = 1, # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update-backup-storage.md b/docs/examples/mysql/update-backup-storage.md new file mode 100644 index 00000000..ecc41eb9 --- /dev/null +++ b/docs/examples/mysql/update-backup-storage.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabaseBackupStorage + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabaseBackupStorage = mysql.update_backup_storage( + database_id = '', + provider = 's3', + bucket = '', + access_key = '', + secret_key = '', + region = '', # optional + prefix = '', # optional + endpoint = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update-credentials.md b/docs/examples/mysql/update-credentials.md new file mode 100644 index 00000000..6555afe7 --- /dev/null +++ b/docs/examples/mysql/update-credentials.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.update_credentials( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update-maintenance.md b/docs/examples/mysql/update-maintenance.md new file mode 100644 index 00000000..a14aa8e8 --- /dev/null +++ b/docs/examples/mysql/update-maintenance.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.update_maintenance( + database_id = '', + day = 'sun', + hour_utc = 0 +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update-pooler.md b/docs/examples/mysql/update-pooler.md new file mode 100644 index 00000000..57fde4e7 --- /dev/null +++ b/docs/examples/mysql/update-pooler.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabasePooler + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabasePooler = mysql.update_pooler( + database_id = '', + mode = 'transaction', # optional + max_connections = 10, # optional + default_pool_size = 1, # optional + read_write_splitting = False, # optional + pooler_cpu_request = '', # optional + pooler_cpu_limit = '', # optional + pooler_memory_request = '', # optional + pooler_memory_limit = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/mysql/update.md b/docs/examples/mysql/update.md new file mode 100644 index 00000000..e3fe2474 --- /dev/null +++ b/docs/examples/mysql/update.md @@ -0,0 +1,38 @@ +```python +from appwrite.client import Client +from appwrite.services.mysql import Mysql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +mysql = Mysql(client) + +result: DedicatedDatabase = mysql.update( + database_id = '', + name = '', # optional + status = 'ready', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0, # optional + metrics_trace_sample_rate = None, # optional + metrics_slow_query_log_threshold_ms = 0, # optional + sql_api_enabled = False, # optional + sql_api_allowed_statements = [], # optional + sql_api_max_rows = 1, # optional + sql_api_max_bytes = 1024, # optional + sql_api_timeout_seconds = 1 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/organization/create-project.md b/docs/examples/organization/create-project.md index 61e03e46..da78ecff 100644 --- a/docs/examples/organization/create-project.md +++ b/docs/examples/organization/create-project.md @@ -12,7 +12,7 @@ client.set_key('') # Your secret API key organization = Organization(client) result: Project = organization.create_project( - project_id = '', + project_id = '', name = '', region = Region.FRA # optional ) diff --git a/docs/examples/postgresql/create-backup-policy.md b/docs/examples/postgresql/create-backup-policy.md new file mode 100644 index 00000000..bb57ff35 --- /dev/null +++ b/docs/examples/postgresql/create-backup-policy.md @@ -0,0 +1,24 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: BackupPolicy = postgresql.create_backup_policy( + database_id = '', + policy_id = '', + name = '', + schedule = '', + retention = 1, + type = 'full', # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-backup.md b/docs/examples/postgresql/create-backup.md new file mode 100644 index 00000000..6123727a --- /dev/null +++ b/docs/examples/postgresql/create-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseBackup = postgresql.create_backup( + database_id = '', + type = 'full' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-branch.md b/docs/examples/postgresql/create-branch.md new file mode 100644 index 00000000..bccd70af --- /dev/null +++ b/docs/examples/postgresql/create-branch.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create_branch( + database_id = '', + branch_id = '', # optional + ttl = 300 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-execution.md b/docs/examples/postgresql/create-execution.md new file mode 100644 index 00000000..4d27ed20 --- /dev/null +++ b/docs/examples/postgresql/create-execution.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseExecution + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseExecution = postgresql.create_execution( + database_id = '', + sql = '', + bindings = {}, # optional + timeout_seconds = 1 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-extension.md b/docs/examples/postgresql/create-extension.md new file mode 100644 index 00000000..507d8968 --- /dev/null +++ b/docs/examples/postgresql/create-extension.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create_extension( + database_id = '', + name = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-failover.md b/docs/examples/postgresql/create-failover.md new file mode 100644 index 00000000..7610a502 --- /dev/null +++ b/docs/examples/postgresql/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-migration.md b/docs/examples/postgresql/create-migration.md new file mode 100644 index 00000000..339e4e6e --- /dev/null +++ b/docs/examples/postgresql/create-migration.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create_migration( + database_id = '', + target_type = 'shared', + specification = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-restoration.md b/docs/examples/postgresql/create-restoration.md new file mode 100644 index 00000000..c4d90b46 --- /dev/null +++ b/docs/examples/postgresql/create-restoration.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseRestoration = postgresql.create_restoration( + database_id = '', + type = 'backup', # optional + backup_id = '', # optional + target_database_id = '', # optional + target_time = '2020-10-15T06:38:00.000+00:00' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create-upgrade.md b/docs/examples/postgresql/create-upgrade.md new file mode 100644 index 00000000..9bbbcb90 --- /dev/null +++ b/docs/examples/postgresql/create-upgrade.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create_upgrade( + database_id = '', + target_version = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/create.md b/docs/examples/postgresql/create.md new file mode 100644 index 00000000..5f1fd90f --- /dev/null +++ b/docs/examples/postgresql/create.md @@ -0,0 +1,31 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.create( + database_id = '', + name = '', + version = '17', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/delete-backup-policy.md b/docs/examples/postgresql/delete-backup-policy.md new file mode 100644 index 00000000..ea285c36 --- /dev/null +++ b/docs/examples/postgresql/delete-backup-policy.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result = postgresql.delete_backup_policy( + database_id = '', + policy_id = '' +) +``` diff --git a/docs/examples/postgresql/delete-backup.md b/docs/examples/postgresql/delete-backup.md new file mode 100644 index 00000000..f4092c31 --- /dev/null +++ b/docs/examples/postgresql/delete-backup.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result = postgresql.delete_backup( + database_id = '', + backup_id = '' +) +``` diff --git a/docs/examples/postgresql/delete-branch.md b/docs/examples/postgresql/delete-branch.md new file mode 100644 index 00000000..1c86002d --- /dev/null +++ b/docs/examples/postgresql/delete-branch.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.delete_branch( + database_id = '', + branch_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/delete-extension.md b/docs/examples/postgresql/delete-extension.md new file mode 100644 index 00000000..f6b09773 --- /dev/null +++ b/docs/examples/postgresql/delete-extension.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.delete_extension( + database_id = '', + extension_name = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/delete.md b/docs/examples/postgresql/delete.md new file mode 100644 index 00000000..3b40a6ce --- /dev/null +++ b/docs/examples/postgresql/delete.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result = postgresql.delete( + database_id = '' +) +``` diff --git a/docs/examples/postgresql/get-backup-policy.md b/docs/examples/postgresql/get-backup-policy.md new file mode 100644 index 00000000..cd1b9445 --- /dev/null +++ b/docs/examples/postgresql/get-backup-policy.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: BackupPolicy = postgresql.get_backup_policy( + database_id = '', + policy_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-backup.md b/docs/examples/postgresql/get-backup.md new file mode 100644 index 00000000..8f226ce4 --- /dev/null +++ b/docs/examples/postgresql/get-backup.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseBackup + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseBackup = postgresql.get_backup( + database_id = '', + backup_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-pitr.md b/docs/examples/postgresql/get-pitr.md new file mode 100644 index 00000000..2c845234 --- /dev/null +++ b/docs/examples/postgresql/get-pitr.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabasePITRWindows + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabasePITRWindows = postgresql.get_pitr( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-pooler.md b/docs/examples/postgresql/get-pooler.md new file mode 100644 index 00000000..3cdfbffb --- /dev/null +++ b/docs/examples/postgresql/get-pooler.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabasePooler + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabasePooler = postgresql.get_pooler( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-replicas.md b/docs/examples/postgresql/get-replicas.md new file mode 100644 index 00000000..e4401f4c --- /dev/null +++ b/docs/examples/postgresql/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseReplicas = postgresql.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-restoration.md b/docs/examples/postgresql/get-restoration.md new file mode 100644 index 00000000..1fb8c412 --- /dev/null +++ b/docs/examples/postgresql/get-restoration.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseRestoration + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseRestoration = postgresql.get_restoration( + database_id = '', + restoration_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get-status.md b/docs/examples/postgresql/get-status.md new file mode 100644 index 00000000..6326f201 --- /dev/null +++ b/docs/examples/postgresql/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DatabaseStatus = postgresql.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/get.md b/docs/examples/postgresql/get.md new file mode 100644 index 00000000..02c21de9 --- /dev/null +++ b/docs/examples/postgresql/get.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.get( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-backup-policies.md b/docs/examples/postgresql/list-backup-policies.md new file mode 100644 index 00000000..c9000c59 --- /dev/null +++ b/docs/examples/postgresql/list-backup-policies.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import BackupPolicyList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: BackupPolicyList = postgresql.list_backup_policies( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-backups.md b/docs/examples/postgresql/list-backups.md new file mode 100644 index 00000000..85622373 --- /dev/null +++ b/docs/examples/postgresql/list-backups.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseBackupList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseBackupList = postgresql.list_backups( + database_id = '', + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-branches.md b/docs/examples/postgresql/list-branches.md new file mode 100644 index 00000000..84f99a84 --- /dev/null +++ b/docs/examples/postgresql/list-branches.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseBranchList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseBranchList = postgresql.list_branches( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-extensions.md b/docs/examples/postgresql/list-extensions.md new file mode 100644 index 00000000..c97c0e3d --- /dev/null +++ b/docs/examples/postgresql/list-extensions.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseExtensions + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseExtensions = postgresql.list_extensions( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-operations.md b/docs/examples/postgresql/list-operations.md new file mode 100644 index 00000000..3575a11d --- /dev/null +++ b/docs/examples/postgresql/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseOperationList = postgresql.list_operations( + database_id = '', + status = 'queued', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-restorations.md b/docs/examples/postgresql/list-restorations.md new file mode 100644 index 00000000..0e70f74b --- /dev/null +++ b/docs/examples/postgresql/list-restorations.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseRestorationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseRestorationList = postgresql.list_restorations( + database_id = '', + status = 'pending', # optional + type = 'backup', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list-specifications.md b/docs/examples/postgresql/list-specifications.md new file mode 100644 index 00000000..c49fdb2e --- /dev/null +++ b/docs/examples/postgresql/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseSpecificationList = postgresql.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/list.md b/docs/examples/postgresql/list.md new file mode 100644 index 00000000..fae83f96 --- /dev/null +++ b/docs/examples/postgresql/list.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseList = postgresql.list( + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update-backup-policy.md b/docs/examples/postgresql/update-backup-policy.md new file mode 100644 index 00000000..02fac735 --- /dev/null +++ b/docs/examples/postgresql/update-backup-policy.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import BackupPolicy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: BackupPolicy = postgresql.update_backup_policy( + database_id = '', + policy_id = '', + name = '', # optional + schedule = '', # optional + retention = 1, # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update-backup-storage.md b/docs/examples/postgresql/update-backup-storage.md new file mode 100644 index 00000000..d0431b4a --- /dev/null +++ b/docs/examples/postgresql/update-backup-storage.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabaseBackupStorage + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabaseBackupStorage = postgresql.update_backup_storage( + database_id = '', + provider = 's3', + bucket = '', + access_key = '', + secret_key = '', + region = '', # optional + prefix = '', # optional + endpoint = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update-credentials.md b/docs/examples/postgresql/update-credentials.md new file mode 100644 index 00000000..b849a932 --- /dev/null +++ b/docs/examples/postgresql/update-credentials.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.update_credentials( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update-maintenance.md b/docs/examples/postgresql/update-maintenance.md new file mode 100644 index 00000000..4795124e --- /dev/null +++ b/docs/examples/postgresql/update-maintenance.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.update_maintenance( + database_id = '', + day = 'sun', + hour_utc = 0 +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update-pooler.md b/docs/examples/postgresql/update-pooler.md new file mode 100644 index 00000000..1f46df6d --- /dev/null +++ b/docs/examples/postgresql/update-pooler.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabasePooler + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabasePooler = postgresql.update_pooler( + database_id = '', + mode = 'transaction', # optional + max_connections = 10, # optional + default_pool_size = 1, # optional + read_write_splitting = False, # optional + pooler_cpu_request = '', # optional + pooler_cpu_limit = '', # optional + pooler_memory_request = '', # optional + pooler_memory_limit = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/postgresql/update.md b/docs/examples/postgresql/update.md new file mode 100644 index 00000000..b6e8ac48 --- /dev/null +++ b/docs/examples/postgresql/update.md @@ -0,0 +1,38 @@ +```python +from appwrite.client import Client +from appwrite.services.postgresql import Postgresql +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +postgresql = Postgresql(client) + +result: DedicatedDatabase = postgresql.update( + database_id = '', + name = '', # optional + status = 'ready', # optional + specification = '', # optional + replicas = 0, # optional + sync_mode = 'async', # optional + network_idle_timeout_seconds = 60, # optional + network_ip_allowlist = [], # optional + idle_timeout_minutes = 5, # optional + pitr = False, # optional + pitr_retention_days = 1, # optional + storage_autoscaling = False, # optional + storage_autoscaling_threshold_percent = 50, # optional + storage_autoscaling_max_gb = 0, # optional + metrics_trace_sample_rate = None, # optional + metrics_slow_query_log_threshold_ms = 0, # optional + sql_api_enabled = False, # optional + sql_api_allowed_statements = [], # optional + sql_api_max_rows = 1, # optional + sql_api_max_bytes = 1024, # optional + sql_api_timeout_seconds = 1 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/project/get-o-auth-2-provider.md b/docs/examples/project/get-o-auth-2-provider.md index f13325e0..0e4ff352 100644 --- a/docs/examples/project/get-o-auth-2-provider.md +++ b/docs/examples/project/get-o-auth-2-provider.md @@ -24,6 +24,7 @@ from appwrite.models import OAuth2Podio from appwrite.models import OAuth2Notion from appwrite.models import OAuth2Salesforce from appwrite.models import OAuth2Yahoo +from appwrite.models import OAuth2HuggingFace from appwrite.models import OAuth2Linkedin from appwrite.models import OAuth2Disqus from appwrite.models import OAuth2Amazon @@ -51,7 +52,7 @@ client.set_key('') # Your secret API key project = Project(client) -result: Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft] = project.get_o_auth2_provider( +result: Union[OAuth2Github, OAuth2Discord, OAuth2Figma, OAuth2Dropbox, OAuth2Dailymotion, OAuth2Bitbucket, OAuth2Bitly, OAuth2Box, OAuth2Autodesk, OAuth2Google, OAuth2Zoom, OAuth2Zoho, OAuth2Yandex, OAuth2X, OAuth2WordPress, OAuth2Twitch, OAuth2Stripe, OAuth2Spotify, OAuth2Slack, OAuth2Podio, OAuth2Notion, OAuth2Salesforce, OAuth2Yahoo, OAuth2HuggingFace, OAuth2Linkedin, OAuth2Disqus, OAuth2Amazon, OAuth2Etsy, OAuth2Facebook, OAuth2Tradeshift, OAuth2Paypal, OAuth2Gitlab, OAuth2Authentik, OAuth2Auth0, OAuth2FusionAuth, OAuth2Keycloak, OAuth2Oidc, OAuth2Apple, OAuth2Okta, OAuth2Kick, OAuth2Microsoft] = project.get_o_auth2_provider( provider_id = ProjectOAuthProviderId.AMAZON ) diff --git a/docs/examples/project/update-o-auth-2-hugging-face.md b/docs/examples/project/update-o-auth-2-hugging-face.md new file mode 100644 index 00000000..932d4af8 --- /dev/null +++ b/docs/examples/project/update-o-auth-2-hugging-face.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.project import Project +from appwrite.models import OAuth2HuggingFace + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +project = Project(client) + +result: OAuth2HuggingFace = project.update_o_auth2_hugging_face( + client_id = '', # optional + client_secret = '', # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/project/update-o-auth-2-okta.md b/docs/examples/project/update-o-auth-2-okta.md index 1bd2e96d..0b4fc532 100644 --- a/docs/examples/project/update-o-auth-2-okta.md +++ b/docs/examples/project/update-o-auth-2-okta.md @@ -13,7 +13,7 @@ project = Project(client) result: OAuth2Okta = project.update_o_auth2_okta( client_id = '', # optional client_secret = '', # optional - domain = '', # optional + domain = 'example.com', # optional authorization_server_id = '', # optional enabled = False # optional ) diff --git a/docs/examples/project/update-smtp.md b/docs/examples/project/update-smtp.md index b5f7847b..772bafea 100644 --- a/docs/examples/project/update-smtp.md +++ b/docs/examples/project/update-smtp.md @@ -12,8 +12,8 @@ client.set_key('') # Your secret API key project = Project(client) result: ProjectModel = project.update_smtp( - host = '', # optional - port = None, # optional + host = 'example.com', # optional + port = 587, # optional username = '', # optional password = 'password', # optional sender_email = 'email@example.com', # optional diff --git a/docs/examples/proxy/create-api-rule.md b/docs/examples/proxy/create-api-rule.md index 5f776309..7baf360c 100644 --- a/docs/examples/proxy/create-api-rule.md +++ b/docs/examples/proxy/create-api-rule.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key proxy = Proxy(client) result: ProxyRule = proxy.create_api_rule( - domain = '' + domain = 'example.com' ) print(result.model_dump()) diff --git a/docs/examples/proxy/create-function-rule.md b/docs/examples/proxy/create-function-rule.md index b28a529d..0abc5926 100644 --- a/docs/examples/proxy/create-function-rule.md +++ b/docs/examples/proxy/create-function-rule.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key proxy = Proxy(client) result: ProxyRule = proxy.create_function_rule( - domain = '', + domain = 'example.com', function_id = '', branch = '' # optional ) diff --git a/docs/examples/proxy/create-invalidation.md b/docs/examples/proxy/create-invalidation.md index f94b4168..413beb6f 100644 --- a/docs/examples/proxy/create-invalidation.md +++ b/docs/examples/proxy/create-invalidation.md @@ -12,7 +12,7 @@ client.set_key('') # Your secret API key proxy = Proxy(client) result: ProxyInvalidation = proxy.create_invalidation( - domain = '', + domain = 'example.com', type = InvalidationType.TAG, reference = '' # optional ) diff --git a/docs/examples/proxy/create-redirect-rule.md b/docs/examples/proxy/create-redirect-rule.md index 6014fbed..7a44bac0 100644 --- a/docs/examples/proxy/create-redirect-rule.md +++ b/docs/examples/proxy/create-redirect-rule.md @@ -13,7 +13,7 @@ client.set_key('') # Your secret API key proxy = Proxy(client) result: ProxyRule = proxy.create_redirect_rule( - domain = '', + domain = 'example.com', url = 'https://example.com', status_code = StatusCode.MOVEDPERMANENTLY, resource_id = '', diff --git a/docs/examples/proxy/create-site-rule.md b/docs/examples/proxy/create-site-rule.md index 54cb0c1e..c108dca6 100644 --- a/docs/examples/proxy/create-site-rule.md +++ b/docs/examples/proxy/create-site-rule.md @@ -11,7 +11,7 @@ client.set_key('') # Your secret API key proxy = Proxy(client) result: ProxyRule = proxy.create_site_rule( - domain = '', + domain = 'example.com', site_id = '', branch = '' # optional ) diff --git a/docs/examples/sites/create.md b/docs/examples/sites/create.md index 684cd054..8fd41e72 100644 --- a/docs/examples/sites/create.md +++ b/docs/examples/sites/create.md @@ -5,6 +5,7 @@ from appwrite.models import Site from appwrite.enums import Framework from appwrite.enums import BuildRuntime from appwrite.enums import Adapter +from appwrite.enums import ProjectKeyScopes client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint @@ -34,9 +35,10 @@ result: Site = sites.create( provider_root_directory = '', # optional provider_branches = [], # optional provider_paths = [], # optional - build_specification = '', # optional - runtime_specification = '', # optional - deployment_retention = 0 # optional + build_specification = 's-1vcpu-512mb', # optional + runtime_specification = 's-1vcpu-512mb', # optional + deployment_retention = 0, # optional + scopes = [ProjectKeyScopes.PROJECT_READ] # optional ) print(result.model_dump()) diff --git a/docs/examples/sites/update.md b/docs/examples/sites/update.md index 2c917b9f..0065e89f 100644 --- a/docs/examples/sites/update.md +++ b/docs/examples/sites/update.md @@ -5,6 +5,7 @@ from appwrite.models import Site from appwrite.enums import Framework from appwrite.enums import BuildRuntime from appwrite.enums import Adapter +from appwrite.enums import ProjectKeyScopes client = Client() client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint @@ -34,9 +35,10 @@ result: Site = sites.update( provider_root_directory = '', # optional provider_branches = [], # optional provider_paths = [], # optional - build_specification = '', # optional - runtime_specification = '', # optional - deployment_retention = 0 # optional + build_specification = 's-1vcpu-512mb', # optional + runtime_specification = 's-1vcpu-512mb', # optional + deployment_retention = 0, # optional + scopes = [ProjectKeyScopes.PROJECT_READ] # optional ) print(result.model_dump()) diff --git a/docs/examples/storage/create-file.md b/docs/examples/storage/create-file.md index cfec75c1..9adb89cf 100644 --- a/docs/examples/storage/create-file.md +++ b/docs/examples/storage/create-file.md @@ -18,7 +18,7 @@ result: File = storage.create_file( file_id = '', file = InputFile.from_path('file.png'), permissions = [Permission.read(Role.any())], # optional - folder = '' # optional + folder = 'photos/2026' # optional ) print(result.model_dump()) diff --git a/docs/examples/storage/get-file-preview.md b/docs/examples/storage/get-file-preview.md index 4cbc4a58..373cb941 100644 --- a/docs/examples/storage/get-file-preview.md +++ b/docs/examples/storage/get-file-preview.md @@ -19,11 +19,11 @@ result: bytes = storage.get_file_preview( gravity = ImageGravity.CENTER, # optional quality = -1, # optional border_width = 0, # optional - border_color = '', # optional + border_color = 'FFFFFF', # optional border_radius = 0, # optional opacity = 0, # optional rotation = -360, # optional - background = '', # optional + background = 'FFFFFF', # optional output = ImageFormat.JPG, # optional token = '' # optional ) diff --git a/docs/examples/tablesdb/create-big-int-column.md b/docs/examples/tablesdb/create-big-int-column.md index 7e4a98c3..cff66960 100644 --- a/docs/examples/tablesdb/create-big-int-column.md +++ b/docs/examples/tablesdb/create-big-int-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnBigint = tables_db.create_big_int_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 1000000, # optional + default = 0, # optional array = False # optional ) diff --git a/docs/examples/tablesdb/create-boolean-column.md b/docs/examples/tablesdb/create-boolean-column.md index a5001168..b325095d 100644 --- a/docs/examples/tablesdb/create-boolean-column.md +++ b/docs/examples/tablesdb/create-boolean-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnBoolean = tables_db.create_boolean_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = False, # optional array = False # optional diff --git a/docs/examples/tablesdb/create-datetime-column.md b/docs/examples/tablesdb/create-datetime-column.md index 4544827b..a4a565d0 100644 --- a/docs/examples/tablesdb/create-datetime-column.md +++ b/docs/examples/tablesdb/create-datetime-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnDatetime = tables_db.create_datetime_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = '2020-10-15T06:38:00.000+00:00', # optional array = False # optional diff --git a/docs/examples/tablesdb/create-email-column.md b/docs/examples/tablesdb/create-email-column.md index b75bd425..7315689c 100644 --- a/docs/examples/tablesdb/create-email-column.md +++ b/docs/examples/tablesdb/create-email-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnEmail = tables_db.create_email_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = 'email@example.com', # optional array = False # optional diff --git a/docs/examples/tablesdb/create-enum-column.md b/docs/examples/tablesdb/create-enum-column.md index a5248b41..3e4cb1b9 100644 --- a/docs/examples/tablesdb/create-enum-column.md +++ b/docs/examples/tablesdb/create-enum-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnEnum = tables_db.create_enum_column( database_id = '', table_id = '', - key = '', - elements = [], + key = '', + elements = ["active", "inactive"], required = False, - default = '', # optional + default = 'active', # optional array = False # optional ) diff --git a/docs/examples/tablesdb/create-float-column.md b/docs/examples/tablesdb/create-float-column.md index 97f414b1..0edd6a26 100644 --- a/docs/examples/tablesdb/create-float-column.md +++ b/docs/examples/tablesdb/create-float-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnFloat = tables_db.create_float_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 100, # optional + default = 10.5, # optional array = False # optional ) diff --git a/docs/examples/tablesdb/create-index.md b/docs/examples/tablesdb/create-index.md index 54b23a25..5de707fe 100644 --- a/docs/examples/tablesdb/create-index.md +++ b/docs/examples/tablesdb/create-index.md @@ -15,7 +15,7 @@ tables_db = TablesDB(client) result: ColumnIndex = tables_db.create_index( database_id = '', table_id = '', - key = '', + key = '', type = TablesDBIndexType.KEY, columns = [], orders = [OrderBy.ASC], # optional diff --git a/docs/examples/tablesdb/create-integer-column.md b/docs/examples/tablesdb/create-integer-column.md index 35ccf417..bbe76889 100644 --- a/docs/examples/tablesdb/create-integer-column.md +++ b/docs/examples/tablesdb/create-integer-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnInteger = tables_db.create_integer_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - min = None, # optional - max = None, # optional - default = None, # optional + min = 0, # optional + max = 100, # optional + default = 10, # optional array = False # optional ) diff --git a/docs/examples/tablesdb/create-ip-column.md b/docs/examples/tablesdb/create-ip-column.md index 71216688..a0a47e67 100644 --- a/docs/examples/tablesdb/create-ip-column.md +++ b/docs/examples/tablesdb/create-ip-column.md @@ -13,9 +13,9 @@ tables_db = TablesDB(client) result: ColumnIp = tables_db.create_ip_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = '192.0.2.0', # optional array = False # optional ) diff --git a/docs/examples/tablesdb/create-line-column.md b/docs/examples/tablesdb/create-line-column.md index 0173466e..2fc64c4f 100644 --- a/docs/examples/tablesdb/create-line-column.md +++ b/docs/examples/tablesdb/create-line-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnLine = tables_db.create_line_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [[1, 2], [3, 4], [5, 6]] # optional ) diff --git a/docs/examples/tablesdb/create-longtext-column.md b/docs/examples/tablesdb/create-longtext-column.md index 29f20903..1438ff8a 100644 --- a/docs/examples/tablesdb/create-longtext-column.md +++ b/docs/examples/tablesdb/create-longtext-column.md @@ -13,9 +13,9 @@ tables_db = TablesDB(client) result: ColumnLongtext = tables_db.create_longtext_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/tablesdb/create-mediumtext-column.md b/docs/examples/tablesdb/create-mediumtext-column.md index 4cdc93ba..6729b329 100644 --- a/docs/examples/tablesdb/create-mediumtext-column.md +++ b/docs/examples/tablesdb/create-mediumtext-column.md @@ -13,9 +13,9 @@ tables_db = TablesDB(client) result: ColumnMediumtext = tables_db.create_mediumtext_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/tablesdb/create-point-column.md b/docs/examples/tablesdb/create-point-column.md index d5dbfce4..17c1e447 100644 --- a/docs/examples/tablesdb/create-point-column.md +++ b/docs/examples/tablesdb/create-point-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnPoint = tables_db.create_point_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [1, 2] # optional ) diff --git a/docs/examples/tablesdb/create-polygon-column.md b/docs/examples/tablesdb/create-polygon-column.md index a21f00a5..86fca304 100644 --- a/docs/examples/tablesdb/create-polygon-column.md +++ b/docs/examples/tablesdb/create-polygon-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnPolygon = tables_db.create_polygon_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [[[1, 2], [3, 4], [5, 6], [1, 2]]] # optional ) diff --git a/docs/examples/tablesdb/create-relationship-column.md b/docs/examples/tablesdb/create-relationship-column.md index 0ec16dbe..ffad0db4 100644 --- a/docs/examples/tablesdb/create-relationship-column.md +++ b/docs/examples/tablesdb/create-relationship-column.md @@ -18,8 +18,8 @@ result: ColumnRelationship = tables_db.create_relationship_column( related_table_id = '', type = RelationshipType.ONETOONE, two_way = False, # optional - key = '', # optional - two_way_key = '', # optional + key = '', # optional + two_way_key = '', # optional on_delete = RelationMutate.CASCADE # optional ) diff --git a/docs/examples/tablesdb/create-string-column.md b/docs/examples/tablesdb/create-string-column.md index 6dae7f9c..85decfde 100644 --- a/docs/examples/tablesdb/create-string-column.md +++ b/docs/examples/tablesdb/create-string-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnString = tables_db.create_string_column( database_id = '', table_id = '', - key = '', + key = '', size = 1, required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/tablesdb/create-text-column.md b/docs/examples/tablesdb/create-text-column.md index 5f8a94db..f3c8df3d 100644 --- a/docs/examples/tablesdb/create-text-column.md +++ b/docs/examples/tablesdb/create-text-column.md @@ -13,9 +13,9 @@ tables_db = TablesDB(client) result: ColumnText = tables_db.create_text_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/tablesdb/create-url-column.md b/docs/examples/tablesdb/create-url-column.md index b37879ac..4bfb858f 100644 --- a/docs/examples/tablesdb/create-url-column.md +++ b/docs/examples/tablesdb/create-url-column.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnUrl = tables_db.create_url_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = 'https://example.com', # optional array = False # optional diff --git a/docs/examples/tablesdb/create-varchar-column.md b/docs/examples/tablesdb/create-varchar-column.md index 02e04101..2fb6338c 100644 --- a/docs/examples/tablesdb/create-varchar-column.md +++ b/docs/examples/tablesdb/create-varchar-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnVarchar = tables_db.create_varchar_column( database_id = '', table_id = '', - key = '', + key = '', size = 1, required = False, - default = '', # optional + default = 'Hello World', # optional array = False, # optional encrypt = False # optional ) diff --git a/docs/examples/tablesdb/decrement-row-column.md b/docs/examples/tablesdb/decrement-row-column.md index f4479022..6ee2f902 100644 --- a/docs/examples/tablesdb/decrement-row-column.md +++ b/docs/examples/tablesdb/decrement-row-column.md @@ -14,9 +14,9 @@ result: Row = tables_db.decrement_row_column( database_id = '', table_id = '', row_id = '', - column = '', - value = None, # optional - min = None, # optional + column = '', + value = 1, # optional + min = 0, # optional transaction_id = '' # optional ) diff --git a/docs/examples/tablesdb/delete-column.md b/docs/examples/tablesdb/delete-column.md index e28b91b1..110fb17f 100644 --- a/docs/examples/tablesdb/delete-column.md +++ b/docs/examples/tablesdb/delete-column.md @@ -12,6 +12,6 @@ tables_db = TablesDB(client) result = tables_db.delete_column( database_id = '', table_id = '', - key = '' + key = '' ) ``` diff --git a/docs/examples/tablesdb/delete-index.md b/docs/examples/tablesdb/delete-index.md index 46379313..8d9e2adf 100644 --- a/docs/examples/tablesdb/delete-index.md +++ b/docs/examples/tablesdb/delete-index.md @@ -12,6 +12,6 @@ tables_db = TablesDB(client) result = tables_db.delete_index( database_id = '', table_id = '', - key = '' + key = '' ) ``` diff --git a/docs/examples/tablesdb/get-column.md b/docs/examples/tablesdb/get-column.md index 77492464..6d2b8255 100644 --- a/docs/examples/tablesdb/get-column.md +++ b/docs/examples/tablesdb/get-column.md @@ -23,7 +23,7 @@ tables_db = TablesDB(client) result: Union[ColumnBoolean, ColumnInteger, ColumnFloat, ColumnEmail, ColumnEnum, ColumnUrl, ColumnIp, ColumnDatetime, ColumnRelationship, ColumnString] = tables_db.get_column( database_id = '', table_id = '', - key = '' + key = '' ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/get-index.md b/docs/examples/tablesdb/get-index.md index 72c8e465..2bce205d 100644 --- a/docs/examples/tablesdb/get-index.md +++ b/docs/examples/tablesdb/get-index.md @@ -13,7 +13,7 @@ tables_db = TablesDB(client) result: ColumnIndex = tables_db.get_index( database_id = '', table_id = '', - key = '' + key = '' ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/increment-row-column.md b/docs/examples/tablesdb/increment-row-column.md index ac844f19..ae25a0b6 100644 --- a/docs/examples/tablesdb/increment-row-column.md +++ b/docs/examples/tablesdb/increment-row-column.md @@ -14,9 +14,9 @@ result: Row = tables_db.increment_row_column( database_id = '', table_id = '', row_id = '', - column = '', - value = None, # optional - max = None, # optional + column = '', + value = 1, # optional + max = 100, # optional transaction_id = '' # optional ) diff --git a/docs/examples/tablesdb/list-operations.md b/docs/examples/tablesdb/list-operations.md index afe14338..aa3754a5 100644 --- a/docs/examples/tablesdb/list-operations.md +++ b/docs/examples/tablesdb/list-operations.md @@ -12,7 +12,7 @@ tables_db = TablesDB(client) result: DedicatedDatabaseOperationList = tables_db.list_operations( database_id = '', - status = 'running', # optional + status = 'queued', # optional limit = 1, # optional offset = 0 # optional ) diff --git a/docs/examples/tablesdb/update-big-int-column.md b/docs/examples/tablesdb/update-big-int-column.md index d395f31a..f4e6e90d 100644 --- a/docs/examples/tablesdb/update-big-int-column.md +++ b/docs/examples/tablesdb/update-big-int-column.md @@ -13,12 +13,12 @@ tables_db = TablesDB(client) result: ColumnBigint = tables_db.update_big_int_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 0, + min = 0, # optional + max = 1000000, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-boolean-column.md b/docs/examples/tablesdb/update-boolean-column.md index ce0a02d9..9352362c 100644 --- a/docs/examples/tablesdb/update-boolean-column.md +++ b/docs/examples/tablesdb/update-boolean-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnBoolean = tables_db.update_boolean_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = False, - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-datetime-column.md b/docs/examples/tablesdb/update-datetime-column.md index 9f9d57aa..70cd5754 100644 --- a/docs/examples/tablesdb/update-datetime-column.md +++ b/docs/examples/tablesdb/update-datetime-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnDatetime = tables_db.update_datetime_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = '2020-10-15T06:38:00.000+00:00', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-email-column.md b/docs/examples/tablesdb/update-email-column.md index 565b941e..94036baf 100644 --- a/docs/examples/tablesdb/update-email-column.md +++ b/docs/examples/tablesdb/update-email-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnEmail = tables_db.update_email_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = 'email@example.com', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-enum-column.md b/docs/examples/tablesdb/update-enum-column.md index 4357a93d..0ac9ac91 100644 --- a/docs/examples/tablesdb/update-enum-column.md +++ b/docs/examples/tablesdb/update-enum-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnEnum = tables_db.update_enum_column( database_id = '', table_id = '', - key = '', - elements = [], + key = '', + elements = ["active", "inactive"], required = False, - default = '', - new_key = '' # optional + default = 'active', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-float-column.md b/docs/examples/tablesdb/update-float-column.md index 339e9c8a..08e39be5 100644 --- a/docs/examples/tablesdb/update-float-column.md +++ b/docs/examples/tablesdb/update-float-column.md @@ -13,12 +13,12 @@ tables_db = TablesDB(client) result: ColumnFloat = tables_db.update_float_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 10.5, + min = 0, # optional + max = 100, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-integer-column.md b/docs/examples/tablesdb/update-integer-column.md index 21a2b1c2..cd6831fc 100644 --- a/docs/examples/tablesdb/update-integer-column.md +++ b/docs/examples/tablesdb/update-integer-column.md @@ -13,12 +13,12 @@ tables_db = TablesDB(client) result: ColumnInteger = tables_db.update_integer_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = None, - min = None, # optional - max = None, # optional - new_key = '' # optional + default = 10, + min = 0, # optional + max = 100, # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-ip-column.md b/docs/examples/tablesdb/update-ip-column.md index cb7e1889..c3570fb1 100644 --- a/docs/examples/tablesdb/update-ip-column.md +++ b/docs/examples/tablesdb/update-ip-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnIp = tables_db.update_ip_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = '192.0.2.0', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-line-column.md b/docs/examples/tablesdb/update-line-column.md index c5bbb5d9..052a12c0 100644 --- a/docs/examples/tablesdb/update-line-column.md +++ b/docs/examples/tablesdb/update-line-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnLine = tables_db.update_line_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [[1, 2], [3, 4], [5, 6]], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-longtext-column.md b/docs/examples/tablesdb/update-longtext-column.md index 8b31f178..8e44bd03 100644 --- a/docs/examples/tablesdb/update-longtext-column.md +++ b/docs/examples/tablesdb/update-longtext-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnLongtext = tables_db.update_longtext_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-mediumtext-column.md b/docs/examples/tablesdb/update-mediumtext-column.md index ad4cdd40..2412dc84 100644 --- a/docs/examples/tablesdb/update-mediumtext-column.md +++ b/docs/examples/tablesdb/update-mediumtext-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnMediumtext = tables_db.update_mediumtext_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-point-column.md b/docs/examples/tablesdb/update-point-column.md index 5ab55846..5368394e 100644 --- a/docs/examples/tablesdb/update-point-column.md +++ b/docs/examples/tablesdb/update-point-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnPoint = tables_db.update_point_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [1, 2], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-polygon-column.md b/docs/examples/tablesdb/update-polygon-column.md index 692a16c0..b7af58ae 100644 --- a/docs/examples/tablesdb/update-polygon-column.md +++ b/docs/examples/tablesdb/update-polygon-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnPolygon = tables_db.update_polygon_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = [[[1, 2], [3, 4], [5, 6], [1, 2]]], # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-relationship-column.md b/docs/examples/tablesdb/update-relationship-column.md index 20307f6d..4932a8a9 100644 --- a/docs/examples/tablesdb/update-relationship-column.md +++ b/docs/examples/tablesdb/update-relationship-column.md @@ -14,9 +14,9 @@ tables_db = TablesDB(client) result: ColumnRelationship = tables_db.update_relationship_column( database_id = '', table_id = '', - key = '', + key = '', on_delete = RelationMutate.CASCADE, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-string-column.md b/docs/examples/tablesdb/update-string-column.md index 0fdc53c7..f3375237 100644 --- a/docs/examples/tablesdb/update-string-column.md +++ b/docs/examples/tablesdb/update-string-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnString = tables_db.update_string_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', + default = 'Hello World', size = 1, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-text-column.md b/docs/examples/tablesdb/update-text-column.md index 3be554c1..21e03944 100644 --- a/docs/examples/tablesdb/update-text-column.md +++ b/docs/examples/tablesdb/update-text-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnText = tables_db.update_text_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', - new_key = '' # optional + default = 'Hello World', + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-url-column.md b/docs/examples/tablesdb/update-url-column.md index 2d8626a2..2553957d 100644 --- a/docs/examples/tablesdb/update-url-column.md +++ b/docs/examples/tablesdb/update-url-column.md @@ -13,10 +13,10 @@ tables_db = TablesDB(client) result: ColumnUrl = tables_db.update_url_column( database_id = '', table_id = '', - key = '', + key = '', required = False, default = 'https://example.com', - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/tablesdb/update-varchar-column.md b/docs/examples/tablesdb/update-varchar-column.md index 1a415b80..3f03b42f 100644 --- a/docs/examples/tablesdb/update-varchar-column.md +++ b/docs/examples/tablesdb/update-varchar-column.md @@ -13,11 +13,11 @@ tables_db = TablesDB(client) result: ColumnVarchar = tables_db.update_varchar_column( database_id = '', table_id = '', - key = '', + key = '', required = False, - default = '', + default = 'Hello World', size = 1, # optional - new_key = '' # optional + new_key = '' # optional ) print(result.model_dump()) diff --git a/docs/examples/users/create-jwt.md b/docs/examples/users/create-jwt.md index bf4df2e0..109ad50a 100644 --- a/docs/examples/users/create-jwt.md +++ b/docs/examples/users/create-jwt.md @@ -12,7 +12,7 @@ users = Users(client) result: Jwt = users.create_jwt( user_id = '', - session_id = '', # optional + session_id = 'recent()', # optional duration = 0 # optional ) diff --git a/docs/examples/users/create-scrypt-user.md b/docs/examples/users/create-scrypt-user.md index db5618be..ecfa6029 100644 --- a/docs/examples/users/create-scrypt-user.md +++ b/docs/examples/users/create-scrypt-user.md @@ -15,10 +15,10 @@ result: User = users.create_scrypt_user( email = 'email@example.com', password = 'password', password_salt = '', - password_cpu = None, - password_memory = None, - password_parallel = None, - password_length = None, + password_cpu = 8, + password_memory = 65536, + password_parallel = 1, + password_length = 64, name = '' # optional ) diff --git a/docs/examples/vectorsdb/create-collection.md b/docs/examples/vectorsdb/create-collection.md new file mode 100644 index 00000000..793aa3f5 --- /dev/null +++ b/docs/examples/vectorsdb/create-collection.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import VectorsdbCollection +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: VectorsdbCollection = vectors_db.create_collection( + database_id = '', + collection_id = '', + name = '', + dimension = 1, + permissions = [Permission.read(Role.any())], # optional + document_security = False, # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-document.md b/docs/examples/vectorsdb/create-document.md new file mode 100644 index 00000000..d032a991 --- /dev/null +++ b/docs/examples/vectorsdb/create-document.md @@ -0,0 +1,34 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: Document = vectors_db.create_document( + database_id = '', + collection_id = '', + document_id = '', + data = { + "embeddings": [ + 0.12, + -0.55, + 0.88, + 1.02 + ], + "metadata": { + "key": "value" + } + }, + permissions = [Permission.read(Role.any())] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-documents.md b/docs/examples/vectorsdb/create-documents.md new file mode 100644 index 00000000..431aec82 --- /dev/null +++ b/docs/examples/vectorsdb/create-documents.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.create_documents( + database_id = '', + collection_id = '', + documents = [] +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-failover.md b/docs/examples/vectorsdb/create-failover.md new file mode 100644 index 00000000..bd8fe7bb --- /dev/null +++ b/docs/examples/vectorsdb/create-failover.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DedicatedDatabase + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DedicatedDatabase = vectors_db.create_failover( + database_id = '', + target_replica_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-index.md b/docs/examples/vectorsdb/create-index.md new file mode 100644 index 00000000..2f5bf256 --- /dev/null +++ b/docs/examples/vectorsdb/create-index.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Index +from appwrite.enums import VectorsDBIndexType +from appwrite.enums import OrderBy + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Index = vectors_db.create_index( + database_id = '', + collection_id = '', + key = '', + type = VectorsDBIndexType.HNSW_EUCLIDEAN, + attributes = [], + orders = [OrderBy.ASC], # optional + lengths = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-operations.md b/docs/examples/vectorsdb/create-operations.md new file mode 100644 index 00000000..e19a8936 --- /dev/null +++ b/docs/examples/vectorsdb/create-operations.md @@ -0,0 +1,29 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Transaction = vectors_db.create_operations( + transaction_id = '', + operations = [ + { + "action": "create", + "databaseId": "", + "collectionId": "", + "documentId": "", + "data": { + "name": "Walter O'Brien" + } + } + ] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-query.md b/docs/examples/vectorsdb/create-query.md new file mode 100644 index 00000000..093a4653 --- /dev/null +++ b/docs/examples/vectorsdb/create-query.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.create_query( + database_id = '', + collection_id = '', + queries = [], # optional + transaction_id = '', # optional + total = False, # optional + ttl = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create-transaction.md b/docs/examples/vectorsdb/create-transaction.md new file mode 100644 index 00000000..6b6cd631 --- /dev/null +++ b/docs/examples/vectorsdb/create-transaction.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Transaction = vectors_db.create_transaction( + ttl = 60 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/create.md b/docs/examples/vectorsdb/create.md new file mode 100644 index 00000000..a77a3a38 --- /dev/null +++ b/docs/examples/vectorsdb/create.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Database = vectors_db.create( + database_id = '', + name = '', + enabled = False, # optional + specification = 'serverless', # optional + replicas = 0, # optional + sync_mode = 'async' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/delete-collection.md b/docs/examples/vectorsdb/delete-collection.md new file mode 100644 index 00000000..b96a628b --- /dev/null +++ b/docs/examples/vectorsdb/delete-collection.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result = vectors_db.delete_collection( + database_id = '', + collection_id = '' +) +``` diff --git a/docs/examples/vectorsdb/delete-document.md b/docs/examples/vectorsdb/delete-document.md new file mode 100644 index 00000000..3915b937 --- /dev/null +++ b/docs/examples/vectorsdb/delete-document.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result = vectors_db.delete_document( + database_id = '', + collection_id = '', + document_id = '', + transaction_id = '' # optional +) +``` diff --git a/docs/examples/vectorsdb/delete-documents.md b/docs/examples/vectorsdb/delete-documents.md new file mode 100644 index 00000000..f1bee6ee --- /dev/null +++ b/docs/examples/vectorsdb/delete-documents.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.delete_documents( + database_id = '', + collection_id = '', + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/delete-index.md b/docs/examples/vectorsdb/delete-index.md new file mode 100644 index 00000000..834b45cc --- /dev/null +++ b/docs/examples/vectorsdb/delete-index.md @@ -0,0 +1,17 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result = vectors_db.delete_index( + database_id = '', + collection_id = '', + key = '' +) +``` diff --git a/docs/examples/vectorsdb/delete-transaction.md b/docs/examples/vectorsdb/delete-transaction.md new file mode 100644 index 00000000..58a367f7 --- /dev/null +++ b/docs/examples/vectorsdb/delete-transaction.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result = vectors_db.delete_transaction( + transaction_id = '' +) +``` diff --git a/docs/examples/vectorsdb/delete.md b/docs/examples/vectorsdb/delete.md new file mode 100644 index 00000000..da1c5a49 --- /dev/null +++ b/docs/examples/vectorsdb/delete.md @@ -0,0 +1,15 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result = vectors_db.delete( + database_id = '' +) +``` diff --git a/docs/examples/vectorsdb/get-collection.md b/docs/examples/vectorsdb/get-collection.md new file mode 100644 index 00000000..2616d72a --- /dev/null +++ b/docs/examples/vectorsdb/get-collection.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import VectorsdbCollection + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: VectorsdbCollection = vectors_db.get_collection( + database_id = '', + collection_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get-document.md b/docs/examples/vectorsdb/get-document.md new file mode 100644 index 00000000..a484c5dd --- /dev/null +++ b/docs/examples/vectorsdb/get-document.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Document + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: Document = vectors_db.get_document( + database_id = '', + collection_id = '', + document_id = '', + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get-index.md b/docs/examples/vectorsdb/get-index.md new file mode 100644 index 00000000..b7a8726b --- /dev/null +++ b/docs/examples/vectorsdb/get-index.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Index + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Index = vectors_db.get_index( + database_id = '', + collection_id = '', + key = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get-replicas.md b/docs/examples/vectorsdb/get-replicas.md new file mode 100644 index 00000000..af8e01ab --- /dev/null +++ b/docs/examples/vectorsdb/get-replicas.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DedicatedDatabaseReplicas + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DedicatedDatabaseReplicas = vectors_db.get_replicas( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get-status.md b/docs/examples/vectorsdb/get-status.md new file mode 100644 index 00000000..8d34903e --- /dev/null +++ b/docs/examples/vectorsdb/get-status.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DatabaseStatus + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DatabaseStatus = vectors_db.get_status( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get-transaction.md b/docs/examples/vectorsdb/get-transaction.md new file mode 100644 index 00000000..601ed0b0 --- /dev/null +++ b/docs/examples/vectorsdb/get-transaction.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Transaction = vectors_db.get_transaction( + transaction_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/get.md b/docs/examples/vectorsdb/get.md new file mode 100644 index 00000000..b251b427 --- /dev/null +++ b/docs/examples/vectorsdb/get.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Database = vectors_db.get( + database_id = '' +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-collections.md b/docs/examples/vectorsdb/list-collections.md new file mode 100644 index 00000000..184c3c3f --- /dev/null +++ b/docs/examples/vectorsdb/list-collections.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import VectorsdbCollectionList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: VectorsdbCollectionList = vectors_db.list_collections( + database_id = '', + queries = [], # optional + search = '', # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-documents.md b/docs/examples/vectorsdb/list-documents.md new file mode 100644 index 00000000..5ac3ab2f --- /dev/null +++ b/docs/examples/vectorsdb/list-documents.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.list_documents( + database_id = '', + collection_id = '', + queries = [], # optional + transaction_id = '', # optional + total = False, # optional + ttl = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-indexes.md b/docs/examples/vectorsdb/list-indexes.md new file mode 100644 index 00000000..c72e9800 --- /dev/null +++ b/docs/examples/vectorsdb/list-indexes.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import IndexList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: IndexList = vectors_db.list_indexes( + database_id = '', + collection_id = '', + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-operations.md b/docs/examples/vectorsdb/list-operations.md new file mode 100644 index 00000000..14f399b7 --- /dev/null +++ b/docs/examples/vectorsdb/list-operations.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DedicatedDatabaseOperationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DedicatedDatabaseOperationList = vectors_db.list_operations( + database_id = '', + status = 'queued', # optional + limit = 1, # optional + offset = 0 # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-specifications.md b/docs/examples/vectorsdb/list-specifications.md new file mode 100644 index 00000000..fdff8182 --- /dev/null +++ b/docs/examples/vectorsdb/list-specifications.md @@ -0,0 +1,16 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DedicatedDatabaseSpecificationList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DedicatedDatabaseSpecificationList = vectors_db.list_specifications() + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list-transactions.md b/docs/examples/vectorsdb/list-transactions.md new file mode 100644 index 00000000..d21db012 --- /dev/null +++ b/docs/examples/vectorsdb/list-transactions.md @@ -0,0 +1,18 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import TransactionList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: TransactionList = vectors_db.list_transactions( + queries = [] # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/list.md b/docs/examples/vectorsdb/list.md new file mode 100644 index 00000000..d7cd9298 --- /dev/null +++ b/docs/examples/vectorsdb/list.md @@ -0,0 +1,19 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DatabaseList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DatabaseList = vectors_db.list( + queries = [], # optional + total = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/update-collection.md b/docs/examples/vectorsdb/update-collection.md new file mode 100644 index 00000000..3dcf8903 --- /dev/null +++ b/docs/examples/vectorsdb/update-collection.md @@ -0,0 +1,26 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import VectorsdbCollection +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: VectorsdbCollection = vectors_db.update_collection( + database_id = '', + collection_id = '', + name = '', + dimension = 1, # optional + permissions = [Permission.read(Role.any())], # optional + document_security = False, # optional + enabled = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/update-document.md b/docs/examples/vectorsdb/update-document.md new file mode 100644 index 00000000..c70c2bc1 --- /dev/null +++ b/docs/examples/vectorsdb/update-document.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: Document = vectors_db.update_document( + database_id = '', + collection_id = '', + document_id = '', + data = {}, # optional + permissions = [Permission.read(Role.any())], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/update-documents.md b/docs/examples/vectorsdb/update-documents.md new file mode 100644 index 00000000..5c947cd1 --- /dev/null +++ b/docs/examples/vectorsdb/update-documents.md @@ -0,0 +1,22 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.update_documents( + database_id = '', + collection_id = '', + data = {}, # optional + queries = [], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/update-transaction.md b/docs/examples/vectorsdb/update-transaction.md new file mode 100644 index 00000000..276c25c8 --- /dev/null +++ b/docs/examples/vectorsdb/update-transaction.md @@ -0,0 +1,20 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Transaction + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Transaction = vectors_db.update_transaction( + transaction_id = '', + commit = False, # optional + rollback = False # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/update.md b/docs/examples/vectorsdb/update.md new file mode 100644 index 00000000..23ae9429 --- /dev/null +++ b/docs/examples/vectorsdb/update.md @@ -0,0 +1,23 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Database + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: Database = vectors_db.update( + database_id = '', + name = '', + enabled = False, # optional + specification = 'serverless', # optional + replicas = 0, # optional + sync_mode = 'async' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/upsert-document.md b/docs/examples/vectorsdb/upsert-document.md new file mode 100644 index 00000000..95f916d3 --- /dev/null +++ b/docs/examples/vectorsdb/upsert-document.md @@ -0,0 +1,25 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import Document +from appwrite.permission import Permission +from appwrite.role import Role + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_session('') # The user session to authenticate with + +vectors_db = VectorsDB(client) + +result: Document = vectors_db.upsert_document( + database_id = '', + collection_id = '', + document_id = '', + data = {}, # optional + permissions = [Permission.read(Role.any())], # optional + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/vectorsdb/upsert-documents.md b/docs/examples/vectorsdb/upsert-documents.md new file mode 100644 index 00000000..5eb3d2d1 --- /dev/null +++ b/docs/examples/vectorsdb/upsert-documents.md @@ -0,0 +1,21 @@ +```python +from appwrite.client import Client +from appwrite.services.vectors_db import VectorsDB +from appwrite.models import DocumentList + +client = Client() +client.set_endpoint('https://.cloud.appwrite.io/v1') # Your API Endpoint +client.set_project('') # Your project ID +client.set_key('') # Your secret API key + +vectors_db = VectorsDB(client) + +result: DocumentList = vectors_db.upsert_documents( + database_id = '', + collection_id = '', + documents = [], + transaction_id = '' # optional +) + +print(result.model_dump()) +``` diff --git a/docs/examples/webhooks/create.md b/docs/examples/webhooks/create.md index 53d45317..ed957a41 100644 --- a/docs/examples/webhooks/create.md +++ b/docs/examples/webhooks/create.md @@ -12,7 +12,7 @@ webhooks = Webhooks(client) result: Webhook = webhooks.create( webhook_id = '', - url = '', + url = 'https://example.com/webhook', name = '', events = [], enabled = False, # optional diff --git a/docs/examples/webhooks/update.md b/docs/examples/webhooks/update.md index b399d55c..a6d3ac7b 100644 --- a/docs/examples/webhooks/update.md +++ b/docs/examples/webhooks/update.md @@ -13,7 +13,7 @@ webhooks = Webhooks(client) result: Webhook = webhooks.update( webhook_id = '', name = '', - url = '', + url = 'https://example.com/webhook', events = [], enabled = False, # optional tls = False, # optional diff --git a/pyproject.toml b/pyproject.toml index f01bffcd..137cee0d 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "23.0.0" +version = "23.1.0rc1" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" @@ -34,6 +34,7 @@ classifiers = [ [project.optional-dependencies] test = [ + "black==25.11.0", "requests_mock==1.11.0", ] @@ -41,5 +42,10 @@ test = [ Homepage = "https://appwrite.io/support" Repository = "https://github.com/appwrite/sdk-for-python" +[tool.black] +line-length = 120 +skip-string-normalization = true +target-version = ['py39'] + [tool.setuptools.packages.find] include = ["appwrite*"] diff --git a/setup.py b/setup.py index 980aaf26..c8a24937 100644 --- a/setup.py +++ b/setup.py @@ -6,34 +6,34 @@ long_description = readme_file_desc.read() setuptools.setup( - name = 'appwrite', - packages = setuptools.find_packages(), - version = '23.0.0', - license='BSD-3-Clause', - description = 'Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', - long_description = long_description, - long_description_content_type = 'text/markdown', - author = 'Appwrite Team', - author_email = 'team@appwrite.io', - maintainer = 'Appwrite Team', - maintainer_email = 'team@appwrite.io', - url = 'https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/23.0.0.tar.gz', - install_requires=[ - 'requests', - 'pydantic>=2,<3', - ], - python_requires='>=3.9', - classifiers=[ - 'Development Status :: 5 - Production/Stable', - 'Intended Audience :: Developers', - 'Environment :: Web Environment', - 'Topic :: Software Development', - 'License :: OSI Approved :: BSD License', - 'Programming Language :: Python :: 3', - 'Programming Language :: Python :: 3.9', - 'Programming Language :: Python :: 3.10', - 'Programming Language :: Python :: 3.11', - 'Programming Language :: Python :: 3.12', - ], + name='appwrite', + packages=setuptools.find_packages(), + version='23.1.0rc1', + license='BSD-3-Clause', + description='Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', + long_description=long_description, + long_description_content_type='text/markdown', + author='Appwrite Team', + author_email='team@appwrite.io', + maintainer='Appwrite Team', + maintainer_email='team@appwrite.io', + url='https://appwrite.io/support', + download_url='https://github.com/appwrite/sdk-for-python/archive/23.1.0rc1.tar.gz', + install_requires=[ + 'requests', + 'pydantic>=2,<3', + ], + python_requires='>=3.9', + classifiers=[ + 'Development Status :: 5 - Production/Stable', + 'Intended Audience :: Developers', + 'Environment :: Web Environment', + 'Topic :: Software Development', + 'License :: OSI Approved :: BSD License', + 'Programming Language :: Python :: 3', + 'Programming Language :: Python :: 3.9', + 'Programming Language :: Python :: 3.10', + 'Programming Language :: Python :: 3.11', + 'Programming Language :: Python :: 3.12', + ], ) diff --git a/test/services/test_account.py b/test/services/test_account.py index 648aba16..ee88a7d8 100644 --- a/test/services/test_account.py +++ b/test/services/test_account.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.account import Account + class AccountServiceTest(unittest.TestCase): def setUp(self): @@ -16,1325 +17,1483 @@ def setUp(self): @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.get( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.get() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_consents(self, m): data = { - "total": 5.0, - "consents": [] -} + "total": 5.0, + "consents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_consents( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_consents() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_consent(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "appId": "5e5ea5c16897e", - "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", - "scopes": [], - "resources": [], - "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.get_consent( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_consent(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_consent( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_consent_tokens(self, m): data = { - "total": 5.0, - "tokens": [] -} + "total": 5.0, + "tokens": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.list_consent_tokens( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_consent_token(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "consentId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "appId": "5e5ea5c16897e", - "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", - "scopes": [], - "resources": [], - "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "consentId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "cimdUrl": "https:\/\/example.com\/.well-known\/client-metadata.json", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.get_consent_token( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_consent_token(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_consent_token( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_email(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_email( 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_identities(self, m): data = { - "total": 5.0, - "identities": [] -} + "total": 5.0, + "identities": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_identities( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_identities() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_identity(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_identity( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_logs(self, m): data = { - "total": 5.0, - "logs": [] -} + "total": 5.0, + "logs": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_logs( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_logs() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_mfa( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_authenticator(self, m): data = { - "secret": "[SHARED_SECRET]", - "uri": "otpauth:\/\/totp\/appwrite:user@example.com?secret=[SHARED_SECRET]&issuer=appwrite" -} + "secret": "[SHARED_SECRET]", + "uri": "otpauth:\/\/totp\/appwrite:user@example.com?secret=[SHARED_SECRET]&issuer=appwrite", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_mfa_authenticator( 'totp', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_authenticator(self, m): data = { - "secret": "[SHARED_SECRET]", - "uri": "otpauth:\/\/totp\/appwrite:user@example.com?secret=[SHARED_SECRET]&issuer=appwrite" -} + "secret": "[SHARED_SECRET]", + "uri": "otpauth:\/\/totp\/appwrite:user@example.com?secret=[SHARED_SECRET]&issuer=appwrite", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_mfa_authenticator( 'totp', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_authenticator(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_mfa_authenticator( 'totp', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_authenticator(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_mfa_authenticator( 'totp', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_mfa_authenticator(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_mfa_authenticator( 'totp', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_delete_mfa_authenticator(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_mfa_authenticator( 'totp', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_mfa_challenge(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_mfa_challenge( 'email', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_challenge(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_mfa_challenge( 'email', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_challenge(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_mfa_challenge( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_challenge(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_mfa_challenge( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_mfa_factors(self, m): data = { - "totp": True, - "phone": True, - "email": True, - "recoveryCode": True, - "custom": True -} + "totp": True, + "phone": True, + "email": True, + "recoveryCode": True, + "custom": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_mfa_factors( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_mfa_factors() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_mfa_factors(self, m): data = { - "totp": True, - "phone": True, - "email": True, - "recoveryCode": True, - "custom": True -} + "totp": True, + "phone": True, + "email": True, + "recoveryCode": True, + "custom": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_mfa_factors( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_mfa_factors() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.get_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.get_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.get_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.get_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.create_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.create_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.create_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.create_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.update_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.update_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.update_mfa_recovery_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.update_mfa_recovery_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_name(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_name( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_password( 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_phone(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_phone( '+12065550100', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_prefs(self, m): data = {} headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.get_prefs( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.get_prefs() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_prefs(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_prefs( {}, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_recovery(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_recovery( 'email@example.com', 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_recovery(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_recovery( '', '', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_sessions(self, m): data = { - "total": 5.0, - "sessions": [] -} + "total": 5.0, + "sessions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.list_sessions( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.list_sessions() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_sessions(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.delete_sessions( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.delete_sessions() self.assertEqual(response, data) @requests_mock.Mocker() def test_create_anonymous_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.create_anonymous_session( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.create_anonymous_session() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email_password_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_email_password_session( 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_magic_url_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_magic_url_session( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_phone_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_phone_session( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_session( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.get_session( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_session( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_session(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.delete_session( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.update_status( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.update_status() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email_token(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_email_token( '', 'email@example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_magic_url_token(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_magic_url_token( '', 'email@example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_o_auth2_token(self, m): data = None headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_o_auth2_token( 'amazon', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_phone_token(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_phone_token( '', '+12065550100', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_email_verification( 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.create_verification( 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_email_verification( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_verification( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_phone_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.account.create_phone_verification( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.account.create_phone_verification() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_phone_verification(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.account.update_phone_verification( '', '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_activities.py b/test/services/test_activities.py index c4b8e550..d9d1e662 100644 --- a/test/services/test_activities.py +++ b/test/services/test_activities.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.activities import Activities + class ActivitiesServiceTest(unittest.TestCase): def setUp(self): @@ -16,56 +17,60 @@ def setUp(self): @requests_mock.Mocker() def test_list_events(self, m): data = { - "total": 5.0, - "events": [] -} + "total": 5.0, + "events": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.activities.list_events( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.activities.list_events() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_event(self, m): data = { - "$id": "5e5ea5c16897e", - "actorType": "user", - "actorId": "610fc2f985ee0", - "actorEmail": "john@appwrite.io", - "actorName": "John Doe", - "resourceParent": "database\/ID", - "resourceType": "collection", - "resourceId": "610fc2f985ee0", - "resource": "collections\/610fc2f985ee0", - "event": "account.sessions.create", - "userAgent": "Mozilla\/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/86.0.4240.198 Safari\/537.36", - "ip": "127.0.0.1", - "mode": "admin", - "country": "US", - "continentCode": "NA", - "city": "Mountain View", - "subdivisions": "California", - "isp": "Google", - "autonomousSystemNumber": "15169", - "autonomousSystemOrganization": "GOOGLE", - "connectionType": "cable", - "connectionUsageType": "residential", - "connectionOrganization": "Google LLC", - "time": "2020-10-15T06:38:00.000+00:00", - "projectId": "610fc2f985ee0", - "teamId": "610fc2f985ee0", - "hostname": "appwrite.io", - "sdk": "web", - "sdkVersion": "14.0.0" -} + "$id": "5e5ea5c16897e", + "actorType": "user", + "actorId": "610fc2f985ee0", + "actorEmail": "john@appwrite.io", + "actorName": "John Doe", + "resourceParent": "database\/ID", + "resourceType": "collection", + "resourceId": "610fc2f985ee0", + "resource": "collections\/610fc2f985ee0", + "event": "account.sessions.create", + "userAgent": "Mozilla\/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/86.0.4240.198 Safari\/537.36", + "ip": "127.0.0.1", + "mode": "admin", + "country": "US", + "continentCode": "NA", + "city": "Mountain View", + "subdivisions": "California", + "isp": "Google", + "autonomousSystemNumber": "15169", + "autonomousSystemOrganization": "GOOGLE", + "connectionType": "cable", + "connectionUsageType": "residential", + "connectionOrganization": "Google LLC", + "time": "2020-10-15T06:38:00.000+00:00", + "projectId": "610fc2f985ee0", + "teamId": "610fc2f985ee0", + "hostname": "appwrite.io", + "sdk": "web", + "sdkVersion": "14.0.0", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.activities.get_event( '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_advisor.py b/test/services/test_advisor.py index 75926cf4..74d8eb1d 100644 --- a/test/services/test_advisor.py +++ b/test/services/test_advisor.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.advisor import Advisor + class AdvisorServiceTest(unittest.TestCase): def setUp(self): @@ -16,93 +17,106 @@ def setUp(self): @requests_mock.Mocker() def test_list_reports(self, m): data = { - "total": 5.0, - "reports": [] -} + "total": 5.0, + "reports": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.advisor.list_reports( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.advisor.list_reports() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_report(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "type": "lighthouse", - "title": "Lighthouse audit for https:\/\/appwrite.io\/", - "summary": "Performance score 78. 4 opportunities found.", - "targetType": "urls", - "target": "https:\/\/appwrite.io\/", - "categories": [], - "insights": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "type": "lighthouse", + "title": "Lighthouse audit for https:\/\/appwrite.io\/", + "summary": "Performance score 78. 4 opportunities found.", + "targetType": "urls", + "target": "https:\/\/appwrite.io\/", + "categories": [], + "insights": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.advisor.get_report( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_report(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.advisor.delete_report( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_insights(self, m): data = { - "total": 5.0, - "insights": [] -} + "total": 5.0, + "insights": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.advisor.list_insights( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_insight(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "reportId": "5e5ea5c16897e", - "type": "tablesDBIndex", - "severity": "warning", - "status": "active", - "resourceType": "databases", - "resourceId": "main", - "parentResourceType": "tables", - "parentResourceId": "orders", - "title": "Missing index on collection orders", - "summary": "Queries against `orders.status` are scanning the full collection.", - "ctas": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "reportId": "5e5ea5c16897e", + "type": "tablesDBIndex", + "severity": "warning", + "status": "active", + "resourceType": "databases", + "resourceId": "main", + "parentResourceType": "tables", + "parentResourceId": "orders", + "title": "Missing index on collection orders", + "summary": "Queries against `orders.status` are scanning the full collection.", + "ctas": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.advisor.get_insight( '', '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_apps.py b/test/services/test_apps.py index 8f9145a3..0e6c2628 100644 --- a/test/services/test_apps.py +++ b/test/services/test_apps.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.apps import Apps + class AppsServiceTest(unittest.TestCase): def setUp(self): @@ -16,478 +17,540 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "apps": [] -} + "total": 5.0, + "apps": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.apps.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.apps.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Application", - "description": "Connect your workspace to My Application.", - "clientUri": "https:\/\/example.com", - "logoUri": "https:\/\/example.com\/logo.png", - "privacyPolicyUrl": "https:\/\/example.com\/privacy", - "termsUrl": "https:\/\/example.com\/terms", - "contacts": [], - "tagline": "Automate your workspace.", - "tags": [], - "labels": [], - "images": [], - "supportUrl": "https:\/\/example.com\/support", - "dataDeletionUrl": "https:\/\/example.com\/data-deletion", - "redirectUris": [], - "postLogoutRedirectUris": [], - "enabled": True, - "type": "confidential", - "deviceFlow": True, - "teamId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "installationScopes": [], - "installationRedirectUrl": "https:\/\/example.com\/setup", - "secrets": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.create( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_installation_scopes(self, m): data = { - "total": 5.0, - "scopes": [] -} + "total": 5.0, + "scopes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.apps.list_installation_scopes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.apps.list_installation_scopes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_o_auth2_scopes(self, m): data = { - "total": 5.0, - "scopes": [] -} + "total": 5.0, + "scopes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.apps.list_o_auth2_scopes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.apps.list_o_auth2_scopes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Application", - "description": "Connect your workspace to My Application.", - "clientUri": "https:\/\/example.com", - "logoUri": "https:\/\/example.com\/logo.png", - "privacyPolicyUrl": "https:\/\/example.com\/privacy", - "termsUrl": "https:\/\/example.com\/terms", - "contacts": [], - "tagline": "Automate your workspace.", - "tags": [], - "labels": [], - "images": [], - "supportUrl": "https:\/\/example.com\/support", - "dataDeletionUrl": "https:\/\/example.com\/data-deletion", - "redirectUris": [], - "postLogoutRedirectUris": [], - "enabled": True, - "type": "confidential", - "deviceFlow": True, - "teamId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "installationScopes": [], - "installationRedirectUrl": "https:\/\/example.com\/setup", - "secrets": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Application", - "description": "Connect your workspace to My Application.", - "clientUri": "https:\/\/example.com", - "logoUri": "https:\/\/example.com\/logo.png", - "privacyPolicyUrl": "https:\/\/example.com\/privacy", - "termsUrl": "https:\/\/example.com\/terms", - "contacts": [], - "tagline": "Automate your workspace.", - "tags": [], - "labels": [], - "images": [], - "supportUrl": "https:\/\/example.com\/support", - "dataDeletionUrl": "https:\/\/example.com\/data-deletion", - "redirectUris": [], - "postLogoutRedirectUris": [], - "enabled": True, - "type": "confidential", - "deviceFlow": True, - "teamId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "installationScopes": [], - "installationRedirectUrl": "https:\/\/example.com\/setup", - "secrets": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.update( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_installations(self, m): data = { - "total": 5.0, - "installations": [] -} + "total": 5.0, + "installations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.list_installations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.get_installation( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_installation(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.delete_installation( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_installation_token(self, m): data = { - "access_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9...", - "token_type": "Bearer", - "expires_in": 3600.0, - "refresh_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...", - "scope": "openid email profile" -} + "access_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9...", + "token_type": "Bearer", + "expires_in": 3600.0, + "refresh_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...", + "scope": "openid email profile", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.create_installation_token( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_keys(self, m): data = { - "total": 5.0, - "keys": [] -} + "total": 5.0, + "keys": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.list_keys( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", - "hint": "f5c6c7", - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.create_key( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", - "hint": "f5c6c7", - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.get_key( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_key(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.delete_key( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_labels(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Application", - "description": "Connect your workspace to My Application.", - "clientUri": "https:\/\/example.com", - "logoUri": "https:\/\/example.com\/logo.png", - "privacyPolicyUrl": "https:\/\/example.com\/privacy", - "termsUrl": "https:\/\/example.com\/terms", - "contacts": [], - "tagline": "Automate your workspace.", - "tags": [], - "labels": [], - "images": [], - "supportUrl": "https:\/\/example.com\/support", - "dataDeletionUrl": "https:\/\/example.com\/data-deletion", - "redirectUris": [], - "postLogoutRedirectUris": [], - "enabled": True, - "type": "confidential", - "deviceFlow": True, - "teamId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "installationScopes": [], - "installationRedirectUrl": "https:\/\/example.com\/setup", - "secrets": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.update_labels( '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_secrets(self, m): data = { - "total": 5.0, - "secrets": [] -} + "total": 5.0, + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.list_secrets( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_secret(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", - "hint": "f5c6c7", - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.create_secret( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_secret(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "secret": "", - "hint": "f5c6c7", - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "secret": "", + "hint": "f5c6c7", + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.get_secret( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_secret(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.delete_secret( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_team(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Application", - "description": "Connect your workspace to My Application.", - "clientUri": "https:\/\/example.com", - "logoUri": "https:\/\/example.com\/logo.png", - "privacyPolicyUrl": "https:\/\/example.com\/privacy", - "termsUrl": "https:\/\/example.com\/terms", - "contacts": [], - "tagline": "Automate your workspace.", - "tags": [], - "labels": [], - "images": [], - "supportUrl": "https:\/\/example.com\/support", - "dataDeletionUrl": "https:\/\/example.com\/data-deletion", - "redirectUris": [], - "postLogoutRedirectUris": [], - "enabled": True, - "type": "confidential", - "deviceFlow": True, - "teamId": "5e5ea5c16897e", - "userId": "5e5ea5c16897e", - "installationScopes": [], - "installationRedirectUrl": "https:\/\/example.com\/setup", - "secrets": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Application", + "description": "Connect your workspace to My Application.", + "clientUri": "https:\/\/example.com", + "logoUri": "https:\/\/example.com\/logo.png", + "privacyPolicyUrl": "https:\/\/example.com\/privacy", + "termsUrl": "https:\/\/example.com\/terms", + "contacts": [], + "tagline": "Automate your workspace.", + "tags": [], + "labels": [], + "images": [], + "supportUrl": "https:\/\/example.com\/support", + "dataDeletionUrl": "https:\/\/example.com\/data-deletion", + "redirectUris": [], + "postLogoutRedirectUris": [], + "enabled": True, + "type": "confidential", + "deviceFlow": True, + "teamId": "5e5ea5c16897e", + "userId": "5e5ea5c16897e", + "installationScopes": [], + "installationRedirectUrl": "https:\/\/example.com\/setup", + "secrets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.update_team( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_tokens(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.apps.delete_tokens( '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_avatars.py b/test/services/test_avatars.py index a37a31e7..b6fc5fbb 100644 --- a/test/services/test_avatars.py +++ b/test/services/test_avatars.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.avatars import Avatars + class AvatarsServiceTest(unittest.TestCase): def setUp(self): @@ -17,94 +18,129 @@ def setUp(self): def test_get_browser(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_browser( 'aa', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_credit_card(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_credit_card( 'amex', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_favicon(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_favicon( 'https://example.com', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_flag(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_flag( 'af', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_image(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_image( 'https://example.com', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_initials(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - - response = self.avatars.get_initials( + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, ) + response = self.avatars.get_initials() + self.assertEqual(response, data) + @requests_mock.Mocker() + def test_get_photo(self, m): + data = bytearray() + headers = {'Content-Type': 'application/octet-stream'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) + response = self.avatars.get_photo() self.assertEqual(response, data) @requests_mock.Mocker() def test_get_qr(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_qr( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_screenshot(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.avatars.get_screenshot( 'https://example.com', ) - self.assertEqual(response, data) - diff --git a/test/services/test_backups.py b/test/services/test_backups.py index 83c59835..a2515204 100644 --- a/test/services/test_backups.py +++ b/test/services/test_backups.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.backups import Backups + class BackupsServiceTest(unittest.TestCase): def setUp(self): @@ -16,233 +17,265 @@ def setUp(self): @requests_mock.Mocker() def test_list_archives(self, m): data = { - "total": 5.0, - "archives": [] -} + "total": 5.0, + "archives": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.backups.list_archives( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.backups.list_archives() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_archive(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "policyId": "did8jx6ws45jana098ab7", - "size": 100000.0, - "status": "completed", - "startedAt": "2020-10-15T06:38:00.000+00:00", - "migrationId": "did8jx6ws45jana098ab7", - "services": [], - "resources": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "policyId": "did8jx6ws45jana098ab7", + "size": 100000.0, + "status": "completed", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "migrationId": "did8jx6ws45jana098ab7", + "services": [], + "resources": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.create_archive( [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_archive(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "policyId": "did8jx6ws45jana098ab7", - "size": 100000.0, - "status": "completed", - "startedAt": "2020-10-15T06:38:00.000+00:00", - "migrationId": "did8jx6ws45jana098ab7", - "services": [], - "resources": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "policyId": "did8jx6ws45jana098ab7", + "size": 100000.0, + "status": "completed", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "migrationId": "did8jx6ws45jana098ab7", + "services": [], + "resources": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.get_archive( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_archive(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.delete_archive( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_policies(self, m): data = { - "total": 5.0, - "policies": [] -} + "total": 5.0, + "policies": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.backups.list_policies( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.backups.list_policies() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "Hourly backups", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "services": [], - "resources": [], - "retention": 7.0, - "schedule": "0 * * * *", - "type": "full", - "enabled": True -} + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.create_policy( '', [], 1, '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "Hourly backups", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "services": [], - "resources": [], - "retention": 7.0, - "schedule": "0 * * * *", - "type": "full", - "enabled": True -} + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.get_policy( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "Hourly backups", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "services": [], - "resources": [], - "retention": 7.0, - "schedule": "0 * * * *", - "type": "full", - "enabled": True -} + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.update_policy( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_policy(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.delete_policy( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_restoration(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "archiveId": "did8jx6ws45jana098ab7", - "policyId": "did8jx6ws45jana098ab7", - "status": "completed", - "startedAt": "2020-10-15T06:38:00.000+00:00", - "migrationId": "did8jx6ws45jana098ab7", - "services": [], - "resources": [], - "options": "{databases.database[{oldId, newId, newName}]}" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "archiveId": "did8jx6ws45jana098ab7", + "policyId": "did8jx6ws45jana098ab7", + "status": "completed", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "migrationId": "did8jx6ws45jana098ab7", + "services": [], + "resources": [], + "options": "{databases.database[{oldId, newId, newName}]}", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.create_restoration( '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_restorations(self, m): data = { - "total": 5.0, - "restorations": [] -} + "total": 5.0, + "restorations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.backups.list_restorations( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.backups.list_restorations() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_restoration(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "archiveId": "did8jx6ws45jana098ab7", - "policyId": "did8jx6ws45jana098ab7", - "status": "completed", - "startedAt": "2020-10-15T06:38:00.000+00:00", - "migrationId": "did8jx6ws45jana098ab7", - "services": [], - "resources": [], - "options": "{databases.database[{oldId, newId, newName}]}" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "archiveId": "did8jx6ws45jana098ab7", + "policyId": "did8jx6ws45jana098ab7", + "status": "completed", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "migrationId": "did8jx6ws45jana098ab7", + "services": [], + "resources": [], + "options": "{databases.database[{oldId, newId, newName}]}", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.backups.get_restoration( '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_databases.py b/test/services/test_databases.py index 11f4ecaf..733f8f08 100644 --- a/test/services/test_databases.py +++ b/test/services/test_databases.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.databases import Databases + class DatabasesServiceTest(unittest.TestCase): def setUp(self): @@ -16,1392 +17,1581 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "databases": [] -} + "total": 5.0, + "databases": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.databases.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.databases.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_transactions(self, m): data = { - "total": 5.0, - "transactions": [] -} + "total": 5.0, + "transactions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.databases.list_transactions( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.databases.list_transactions() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.databases.create_transaction( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.databases.create_transaction() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get_transaction( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_transaction( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_transaction(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_transaction( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_operations(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_operations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_collections(self, m): data = { - "total": 5.0, - "collections": [] -} + "total": 5.0, + "collections": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.list_collections( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_collection(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Collection", - "enabled": True, - "documentSecurity": True, - "attributes": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_collection( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_collection(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Collection", - "enabled": True, - "documentSecurity": True, - "attributes": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get_collection( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_collection(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Collection", - "enabled": True, - "documentSecurity": True, - "attributes": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_collection( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_collection(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_collection( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_attributes(self, m): data = { - "total": 5.0, - "attributes": [] -} + "total": 5.0, + "attributes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.list_attributes( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_big_int_attribute(self, m): data = { - "key": "count", - "type": "bigint", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "bigint", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_big_int_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_big_int_attribute(self, m): data = { - "key": "count", - "type": "bigint", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "bigint", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_big_int_attribute( '', '', - '', + '', True, 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_boolean_attribute(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_boolean_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_boolean_attribute(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_boolean_attribute( '', '', - '', + '', True, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_datetime_attribute(self, m): data = { - "key": "birthDay", - "type": "datetime", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "datetime" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "birthDay", + "type": "datetime", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "datetime", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_datetime_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_datetime_attribute(self, m): data = { - "key": "birthDay", - "type": "datetime", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "datetime" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "birthDay", + "type": "datetime", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "datetime", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_datetime_attribute( '', '', - '', + '', True, '2020-10-15T06:38:00.000+00:00', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email_attribute(self, m): data = { - "key": "userEmail", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "email" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "userEmail", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "email", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_email_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email_attribute(self, m): data = { - "key": "userEmail", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "email" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "userEmail", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "email", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_email_attribute( '', '', - '', + '', True, 'email@example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_enum_attribute(self, m): data = { - "key": "status", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "elements": [], - "format": "enum" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "status", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "elements": [], + "format": "enum", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_enum_attribute( '', '', - '', + '', [], True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_enum_attribute(self, m): data = { - "key": "status", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "elements": [], - "format": "enum" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "status", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "elements": [], + "format": "enum", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_enum_attribute( '', '', - '', + '', [], True, - '', + 'active', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_float_attribute(self, m): data = { - "key": "percentageCompleted", - "type": "double", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "percentageCompleted", + "type": "double", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_float_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_float_attribute(self, m): data = { - "key": "percentageCompleted", - "type": "double", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "percentageCompleted", + "type": "double", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_float_attribute( '', '', - '', + '', True, 1.0, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_integer_attribute(self, m): data = { - "key": "count", - "type": "integer", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "integer", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_integer_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_integer_attribute(self, m): data = { - "key": "count", - "type": "integer", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "integer", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_integer_attribute( '', '', - '', + '', True, 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_ip_attribute(self, m): data = { - "key": "ipAddress", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "ip" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "ipAddress", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "ip", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_ip_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_ip_attribute(self, m): data = { - "key": "ipAddress", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "ip" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "ipAddress", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "ip", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_ip_attribute( '', '', - '', + '', True, - '', + '192.0.2.0', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_line_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_line_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_line_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_line_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_longtext_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_longtext_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_longtext_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_longtext_attribute( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mediumtext_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_mediumtext_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mediumtext_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_mediumtext_attribute( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_point_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_point_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_point_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_point_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_polygon_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_polygon_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_polygon_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_polygon_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_relationship_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "relatedCollection": "collection", - "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", - "twoWay": True, - "twoWayKey": "string", - "onDelete": "restrict|cascade|setNull", - "side": "parent|child" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "relatedCollection": "collection", + "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", + "twoWay": True, + "twoWayKey": "string", + "onDelete": "restrict|cascade|setNull", + "side": "parent|child", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_relationship_attribute( '', '', '', 'oneToOne', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_relationship_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "relatedCollection": "collection", - "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", - "twoWay": True, - "twoWayKey": "string", - "onDelete": "restrict|cascade|setNull", - "side": "parent|child" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "relatedCollection": "collection", + "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", + "twoWay": True, + "twoWayKey": "string", + "onDelete": "restrict|cascade|setNull", + "side": "parent|child", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_relationship_attribute( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_string_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_string_attribute( '', '', - '', + '', 1, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_string_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_string_attribute( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_text_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_text_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_text_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_text_attribute( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_url_attribute(self, m): data = { - "key": "githubUrl", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "url" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "githubUrl", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "url", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_url_attribute( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_url_attribute(self, m): data = { - "key": "githubUrl", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "url" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "githubUrl", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "url", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_url_attribute( '', '', - '', + '', True, 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_varchar_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_varchar_attribute( '', '', - '', + '', 1, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_varchar_attribute(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_varchar_attribute( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_attribute(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get_attribute( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_attribute(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_attribute( '', '', - '', + '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_documents(self, m): data = { - "total": 5.0, - "documents": [] -} + "total": 5.0, + "documents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.list_documents( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_document(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_document( '', '', '', {}, ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_documents(self, m): data = { - "total": 5.0, - "documents": [] -} + "total": 5.0, + "documents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_documents( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_upsert_documents(self, m): data = { - "total": 5.0, - "documents": [] -} + "total": 5.0, + "documents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.upsert_documents( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_documents(self, m): data = { - "total": 5.0, - "documents": [] -} + "total": 5.0, + "documents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_documents( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_documents(self, m): data = { - "total": 5.0, - "documents": [] -} + "total": 5.0, + "documents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_documents( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_document(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get_document( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_upsert_document(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.upsert_document( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_document(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.update_document( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @@ -1409,141 +1599,161 @@ def test_update_document(self, m): def test_delete_document(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_document( '', '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_decrement_document_attribute(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.decrement_document_attribute( '', '', '', - '', + '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_increment_document_attribute(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$collectionId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.increment_document_attribute( '', '', '', - '', + '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_indexes(self, m): data = { - "total": 5.0, - "indexes": [] -} + "total": 5.0, + "indexes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.list_indexes( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_index(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "index1", - "type": "primary", - "status": "available", - "error": "string", - "attributes": [], - "lengths": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.create_index( '', '', - '', + '', 'key', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_index(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "index1", - "type": "primary", - "status": "available", - "error": "string", - "attributes": [], - "lengths": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.get_index( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_index(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.databases.delete_index( '', '', - '', + '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_documents_db.py b/test/services/test_documents_db.py new file mode 100644 index 00000000..06c50949 --- /dev/null +++ b/test/services/test_documents_db.py @@ -0,0 +1,874 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.documents_db import DocumentsDB + + +class DocumentsDBServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.documents_db = DocumentsDB(self.client) + + @requests_mock.Mocker() + def test_list(self, m): + data = { + "total": 5.0, + "databases": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_specifications() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_transactions(self, m): + data = { + "total": 5.0, + "transactions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_transactions() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_transaction() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_transaction( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.update_transaction( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_transaction(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete_transaction( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_create_operations(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.update( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_collections(self, m): + data = { + "total": 5.0, + "collections": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_collections( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_collection( + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_collection( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.update_collection( + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_collection(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete_collection( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_document( + '', + '', + '', + {}, + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_documents( + '', + '', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_upsert_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.upsert_documents( + '', + '', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.update_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_upsert_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.upsert_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.update_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_document(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete_document( + '', + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_decrement_document_attribute(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.decrement_document_attribute( + '', + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_increment_document_attribute(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.increment_document_attribute( + '', + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_indexes(self, m): + data = { + "total": 5.0, + "indexes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_indexes( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_index(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_index( + '', + '', + '', + 'key', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_index(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_index( + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_index(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.delete_index( + '', + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.create_failover( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.list_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_replicas( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.documents_db.get_status( + '', + ) + self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_embeddings.py b/test/services/test_embeddings.py index 8d2cf848..4c37d10d 100644 --- a/test/services/test_embeddings.py +++ b/test/services/test_embeddings.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.embeddings import Embeddings + class EmbeddingsServiceTest(unittest.TestCase): def setUp(self): @@ -16,15 +17,17 @@ def setUp(self): @requests_mock.Mocker() def test_create_text_embeddings(self, m): data = { - "total": 5.0, - "embeddings": [] -} + "total": 5.0, + "embeddings": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.embeddings.create_text_embeddings( [], ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_functions.py b/test/services/test_functions.py index 411d41e1..16a21555 100644 --- a/test/services/test_functions.py +++ b/test/services/test_functions.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.functions import Functions + class FunctionsServiceTest(unittest.TestCase): def setUp(self): @@ -16,373 +17,407 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "functions": [] -} + "total": 5.0, + "functions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.functions.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.functions.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "execute": [], - "name": "My Function", - "enabled": True, - "live": True, - "logging": True, - "runtime": "python-3.8", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "scopes": [], - "vars": [], - "events": [], - "schedule": "5 4 * * *", - "timeout": 300.0, - "entrypoint": "index.js", - "commands": "npm install", - "version": "v2", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "functions\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "execute": [], + "name": "My Function", + "enabled": True, + "live": True, + "logging": True, + "runtime": "python-3.8", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "events": [], + "schedule": "5 4 * * *", + "timeout": 300.0, + "entrypoint": "index.js", + "commands": "npm install", + "version": "v2", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "functions\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create( '', '', 'node-14.5', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_runtimes(self, m): data = { - "total": 5.0, - "runtimes": [] -} + "total": 5.0, + "runtimes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.functions.list_runtimes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.functions.list_runtimes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_specifications(self, m): data = { - "total": 5.0, - "specifications": [] -} + "total": 5.0, + "specifications": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.functions.list_specifications( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.functions.list_specifications() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "execute": [], - "name": "My Function", - "enabled": True, - "live": True, - "logging": True, - "runtime": "python-3.8", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "scopes": [], - "vars": [], - "events": [], - "schedule": "5 4 * * *", - "timeout": 300.0, - "entrypoint": "index.js", - "commands": "npm install", - "version": "v2", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "functions\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "execute": [], + "name": "My Function", + "enabled": True, + "live": True, + "logging": True, + "runtime": "python-3.8", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "events": [], + "schedule": "5 4 * * *", + "timeout": 300.0, + "entrypoint": "index.js", + "commands": "npm install", + "version": "v2", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "functions\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "execute": [], - "name": "My Function", - "enabled": True, - "live": True, - "logging": True, - "runtime": "python-3.8", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "scopes": [], - "vars": [], - "events": [], - "schedule": "5 4 * * *", - "timeout": 300.0, - "entrypoint": "index.js", - "commands": "npm install", - "version": "v2", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "functions\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "execute": [], + "name": "My Function", + "enabled": True, + "live": True, + "logging": True, + "runtime": "python-3.8", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "events": [], + "schedule": "5 4 * * *", + "timeout": 300.0, + "entrypoint": "index.js", + "commands": "npm install", + "version": "v2", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "functions\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.update( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_function_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "execute": [], - "name": "My Function", - "enabled": True, - "live": True, - "logging": True, - "runtime": "python-3.8", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "scopes": [], - "vars": [], - "events": [], - "schedule": "5 4 * * *", - "timeout": 300.0, - "entrypoint": "index.js", - "commands": "npm install", - "version": "v2", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "functions\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "execute": [], + "name": "My Function", + "enabled": True, + "live": True, + "logging": True, + "runtime": "python-3.8", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "events": [], + "schedule": "5 4 * * *", + "timeout": 300.0, + "entrypoint": "index.js", + "commands": "npm install", + "version": "v2", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "functions\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.update_function_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_deployments(self, m): data = { - "total": 5.0, - "deployments": [] -} + "total": 5.0, + "deployments": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.list_deployments( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_deployment( '', InputFile.from_bytes(bytearray(), "example.file"), True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_duplicate_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_duplicate_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_template_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_template_deployment( '', '', @@ -391,341 +426,383 @@ def test_create_template_deployment(self, m): 'commit', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_vcs_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_vcs_deployment( '', 'branch', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.get_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_deployment(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.delete_deployment( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_deployment_download(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.functions.get_deployment_download( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_deployment_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.update_deployment_status( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_executions(self, m): data = { - "total": 5.0, - "executions": [] -} + "total": 5.0, + "executions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.list_executions( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_execution(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "functionId": "5e5ea6g16897e", - "deploymentId": "5e5ea5c16897e", - "trigger": "http", - "status": "processing", - "requestMethod": "GET", - "requestPath": "\/articles?id=5", - "requestHeaders": [], - "responseStatusCode": 200.0, - "responseBody": "", - "responseHeaders": [], - "logs": "", - "errors": "", - "duration": 0.4 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "deploymentId": "5e5ea5c16897e", + "trigger": "http", + "status": "processing", + "requestMethod": "GET", + "requestPath": "\/articles?id=5", + "requestHeaders": [], + "responseStatusCode": 200.0, + "responseBody": "", + "responseHeaders": [], + "logs": "", + "errors": "", + "duration": 0.4, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_execution( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_execution(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "functionId": "5e5ea6g16897e", - "deploymentId": "5e5ea5c16897e", - "trigger": "http", - "status": "processing", - "requestMethod": "GET", - "requestPath": "\/articles?id=5", - "requestHeaders": [], - "responseStatusCode": 200.0, - "responseBody": "", - "responseHeaders": [], - "logs": "", - "errors": "", - "duration": 0.4 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "deploymentId": "5e5ea5c16897e", + "trigger": "http", + "status": "processing", + "requestMethod": "GET", + "requestPath": "\/articles?id=5", + "requestHeaders": [], + "responseStatusCode": 200.0, + "responseBody": "", + "responseHeaders": [], + "logs": "", + "errors": "", + "duration": 0.4, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.get_execution( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_execution(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.delete_execution( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_variables(self, m): data = { - "total": 5.0, - "variables": [] -} + "total": 5.0, + "variables": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.list_variables( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.create_variable( '', '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.get_variable( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.update_variable( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_variable(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.functions.delete_variable( '', '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_graphql.py b/test/services/test_graphql.py index 72a69f46..d9203da8 100644 --- a/test/services/test_graphql.py +++ b/test/services/test_graphql.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.graphql import Graphql + class GraphqlServiceTest(unittest.TestCase): def setUp(self): @@ -17,23 +18,28 @@ def setUp(self): def test_query(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.graphql.query( {}, ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_mutation(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.graphql.mutation( {}, ) - self.assertEqual(response, data) - diff --git a/test/services/test_locale.py b/test/services/test_locale.py index 00c016f1..1438edfb 100644 --- a/test/services/test_locale.py +++ b/test/services/test_locale.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.locale import Locale + class LocaleServiceTest(unittest.TestCase): def setUp(self): @@ -16,117 +17,132 @@ def setUp(self): @requests_mock.Mocker() def test_get(self, m): data = { - "ip": "127.0.0.1", - "countryCode": "US", - "country": "United States", - "continentCode": "NA", - "continent": "North America", - "eu": True, - "currency": "USD" -} + "ip": "127.0.0.1", + "countryCode": "US", + "country": "United States", + "continentCode": "NA", + "continent": "North America", + "eu": True, + "currency": "USD", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.get( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.get() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_codes(self, m): data = { - "total": 5.0, - "localeCodes": [] -} + "total": 5.0, + "localeCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_codes( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_codes() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_continents(self, m): data = { - "total": 5.0, - "continents": [] -} + "total": 5.0, + "continents": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_continents( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_continents() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_countries(self, m): data = { - "total": 5.0, - "countries": [] -} + "total": 5.0, + "countries": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_countries( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_countries() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_countries_eu(self, m): data = { - "total": 5.0, - "countries": [] -} + "total": 5.0, + "countries": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_countries_eu( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_countries_eu() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_countries_phones(self, m): data = { - "total": 5.0, - "phones": [] -} + "total": 5.0, + "phones": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_countries_phones( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_countries_phones() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_currencies(self, m): data = { - "total": 5.0, - "currencies": [] -} + "total": 5.0, + "currencies": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_currencies( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_currencies() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_languages(self, m): data = { - "total": 5.0, - "languages": [] -} + "total": 5.0, + "languages": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.locale.list_languages( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.locale.list_languages() self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_messaging.py b/test/services/test_messaging.py index ef6d618d..ad69b926 100644 --- a/test/services/test_messaging.py +++ b/test/services/test_messaging.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.messaging import Messaging + class MessagingServiceTest(unittest.TestCase): def setUp(self): @@ -16,1129 +17,1287 @@ def setUp(self): @requests_mock.Mocker() def test_list_messages(self, m): data = { - "total": 5.0, - "messages": [] -} + "total": 5.0, + "messages": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_messages( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.messaging.list_messages() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_email( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_email( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_push(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_push( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_push(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_push( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_sms(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_sms( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_sms(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_sms( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_sms(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_sms( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_sms(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_sms( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_message(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "providerType": "email", - "topics": [], - "users": [], - "targets": [], - "deliveredTotal": 1.0, - "data": {}, - "status": "processing" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "providerType": "email", + "topics": [], + "users": [], + "targets": [], + "deliveredTotal": 1.0, + "data": {}, + "status": "processing", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.get_message( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_targets(self, m): data = { - "total": 5.0, - "targets": [] -} + "total": 5.0, + "targets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.list_targets( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_providers(self, m): data = { - "total": 5.0, - "providers": [] -} + "total": 5.0, + "providers": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_providers( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.messaging.list_providers() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_apns_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_apns_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_apns_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_apns_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_apns_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_apns_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_apns_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_apns_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_fcm_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_fcm_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_fcm_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_fcm_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_fcm_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_fcm_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_fcm_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_fcm_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mailgun_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_mailgun_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mailgun_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_mailgun_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_msg91_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_msg91_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_msg91_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_msg91_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_resend_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_resend_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_resend_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_resend_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_sendgrid_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_sendgrid_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_sendgrid_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_sendgrid_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_ses_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_ses_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_ses_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_ses_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_smtp_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_smtp_provider( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_smtp_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_smtp_provider( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_smtp_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_smtp_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_smtp_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_smtp_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_telesign_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_telesign_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_telesign_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_telesign_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_textmagic_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_textmagic_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_textmagic_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_textmagic_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_twilio_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_twilio_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_twilio_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_twilio_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_vonage_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_vonage_provider( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_vonage_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_vonage_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_provider(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Mailgun", - "provider": "mailgun", - "enabled": True, - "type": "sms", - "credentials": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Mailgun", + "provider": "mailgun", + "enabled": True, + "type": "sms", + "credentials": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.get_provider( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_provider(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.delete_provider( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_topics(self, m): data = { - "total": 5.0, - "topics": [] -} + "total": 5.0, + "topics": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.messaging.list_topics( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.messaging.list_topics() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_topic(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "events", - "emailTotal": 100.0, - "smsTotal": 100.0, - "pushTotal": 100.0, - "subscribe": [] -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "events", + "emailTotal": 100.0, + "smsTotal": 100.0, + "pushTotal": 100.0, + "subscribe": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_topic( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_topic(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "events", - "emailTotal": 100.0, - "smsTotal": 100.0, - "pushTotal": 100.0, - "subscribe": [] -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "events", + "emailTotal": 100.0, + "smsTotal": 100.0, + "pushTotal": 100.0, + "subscribe": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.get_topic( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_topic(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "events", - "emailTotal": 100.0, - "smsTotal": 100.0, - "pushTotal": 100.0, - "subscribe": [] -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "events", + "emailTotal": 100.0, + "smsTotal": 100.0, + "pushTotal": 100.0, + "subscribe": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.update_topic( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_topic(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.delete_topic( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_subscribers(self, m): data = { - "total": 5.0, - "subscribers": [] -} + "total": 5.0, + "subscribers": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.list_subscribers( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_subscriber(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "targetId": "259125845563242502", - "target": { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Apple iPhone 12", - "userId": "259125845563242502", - "providerType": "email", - "identifier": "token", - "expired": True - }, - "userId": "5e5ea5c16897e", - "userName": "Aegon Targaryen", - "topicId": "259125845563242502", - "providerType": "email" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "targetId": "259125845563242502", + "target": { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Apple iPhone 12", + "userId": "259125845563242502", + "providerType": "email", + "identifier": "token", + "expired": True, + }, + "userId": "5e5ea5c16897e", + "userName": "Aegon Targaryen", + "topicId": "259125845563242502", + "providerType": "email", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.create_subscriber( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_subscriber(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "targetId": "259125845563242502", - "target": { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Apple iPhone 12", - "userId": "259125845563242502", - "providerType": "email", - "identifier": "token", - "expired": True - }, - "userId": "5e5ea5c16897e", - "userName": "Aegon Targaryen", - "topicId": "259125845563242502", - "providerType": "email" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "targetId": "259125845563242502", + "target": { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Apple iPhone 12", + "userId": "259125845563242502", + "providerType": "email", + "identifier": "token", + "expired": True, + }, + "userId": "5e5ea5c16897e", + "userName": "Aegon Targaryen", + "topicId": "259125845563242502", + "providerType": "email", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.get_subscriber( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_subscriber(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.messaging.delete_subscriber( '', '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_mongo.py b/test/services/test_mongo.py new file mode 100644 index 00000000..3e26ffc9 --- /dev/null +++ b/test/services/test_mongo.py @@ -0,0 +1,1110 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.mongo import Mongo + + +class MongoServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.mongo = Mongo(self.client) + + @requests_mock.Mocker() + def test_list(self, m): + data = { + "total": 5.0, + "databases": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_specifications() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.update( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.delete( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_backups(self, m): + data = { + "total": 5.0, + "backups": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_backups( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_backup( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_backup_policies(self, m): + data = { + "total": 5.0, + "policies": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_backup_policies( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_backup_policy( + '', + '', + '', + '', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.update_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup_policy(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.delete_backup_policy( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_update_backup_storage(self, m): + data = { + "provider": "s3", + "bucket": "my-backup-bucket", + "region": "us-east-1", + "prefix": "backups\/", + "endpoint": "https:\/\/minio.example.com", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.update_backup_storage( + '', + 's3', + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_backup( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.delete_backup( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_branches(self, m): + data = { + "total": 2.0, + "branches": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_branches( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_branch( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.delete_branch( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_credentials(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.update_credentials( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_failover( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_maintenance(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.update_maintenance( + '', + 'sun', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_migration( + '', + 'shared', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_pitr(self, m): + data = { + "earliest": "2020-10-15T06:38:00.000+00:00", + "latest": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_pitr( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_replicas( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_restorations(self, m): + data = { + "total": 5.0, + "restorations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.list_restorations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_restoration( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_restoration( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.get_status( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_upgrade(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mongo.create_upgrade( + '', + '', + ) + self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_mysql.py b/test/services/test_mysql.py new file mode 100644 index 00000000..271b3999 --- /dev/null +++ b/test/services/test_mysql.py @@ -0,0 +1,1185 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.mysql import Mysql + + +class MysqlServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.mysql = Mysql(self.client) + + @requests_mock.Mocker() + def test_list(self, m): + data = { + "total": 5.0, + "databases": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_specifications() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.delete( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_backups(self, m): + data = { + "total": 5.0, + "backups": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_backups( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_backup( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_backup_policies(self, m): + data = { + "total": 5.0, + "policies": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_backup_policies( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_backup_policy( + '', + '', + '', + '', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup_policy(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.delete_backup_policy( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_update_backup_storage(self, m): + data = { + "provider": "s3", + "bucket": "my-backup-bucket", + "region": "us-east-1", + "prefix": "backups\/", + "endpoint": "https:\/\/minio.example.com", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update_backup_storage( + '', + 's3', + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_backup( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.delete_backup( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_branches(self, m): + data = { + "total": 2.0, + "branches": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_branches( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_branch( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.delete_branch( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_credentials(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update_credentials( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_execution(self, m): + data = { + "rows": [], + "rowCount": 1.0, + "columns": [], + "durationMs": 12.0, + "truncated": True, + "bytes": 1024.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_execution( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_failover( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_maintenance(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update_maintenance( + '', + 'sun', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_migration( + '', + 'shared', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_pitr(self, m): + data = { + "earliest": "2020-10-15T06:38:00.000+00:00", + "latest": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_pitr( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_pooler(self, m): + data = { + "enabled": True, + "mode": "transaction", + "maxConnections": 200.0, + "defaultPoolSize": 25.0, + "port": 6432.0, + "readWriteSplitting": True, + "poolerCpuRequest": "100m", + "poolerCpuLimit": "200m", + "poolerMemoryRequest": "64Mi", + "poolerMemoryLimit": "128Mi", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_pooler( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_pooler(self, m): + data = { + "enabled": True, + "mode": "transaction", + "maxConnections": 200.0, + "defaultPoolSize": 25.0, + "port": 6432.0, + "readWriteSplitting": True, + "poolerCpuRequest": "100m", + "poolerCpuLimit": "200m", + "poolerMemoryRequest": "64Mi", + "poolerMemoryLimit": "128Mi", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.update_pooler( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_replicas( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_restorations(self, m): + data = { + "total": 5.0, + "restorations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.list_restorations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_restoration( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_restoration( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.get_status( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_upgrade(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.mysql.create_upgrade( + '', + '', + ) + self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_oauth2.py b/test/services/test_oauth2.py index 0f331808..5365456d 100644 --- a/test/services/test_oauth2.py +++ b/test/services/test_oauth2.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.oauth2 import Oauth2 + class Oauth2ServiceTest(unittest.TestCase): def setUp(self): @@ -16,199 +17,229 @@ def setUp(self): @requests_mock.Mocker() def test_approve(self, m): data = { - "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij" -} + "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.approve( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_authorize(self, m): data = { - "grantId": "5e5ea5c16897e", - "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij" -} + "grantId": "5e5ea5c16897e", + "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.oauth2.authorize( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.oauth2.authorize() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_authorize_post(self, m): data = { - "grantId": "5e5ea5c16897e", - "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij" -} + "grantId": "5e5ea5c16897e", + "redirectUrl": "https:\/\/example.com\/callback?code=abcde&state=fghij", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.oauth2.authorize_post( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.oauth2.authorize_post() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_device_authorization(self, m): data = { - "device_code": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", - "user_code": "ABCD-EFGH", - "verification_uri": "https:\/\/cloud.appwrite.io\/console\/oauth2\/device", - "verification_uri_complete": "https:\/\/cloud.appwrite.io\/console\/oauth2\/device?user_code=ABCD-EFGH", - "expires_in": 900.0, - "interval": 5.0 -} + "device_code": "5f3c8d2a1b9e4f7a6c8b2d1e9f4a7b3c5d8e1f2a9b4c7d6e3f5a8b1c4d7e2f9a", + "user_code": "ABCD-EFGH", + "verification_uri": "https:\/\/cloud.appwrite.io\/console\/oauth2\/device", + "verification_uri_complete": "https:\/\/cloud.appwrite.io\/console\/oauth2\/device?user_code=ABCD-EFGH", + "expires_in": 900.0, + "interval": 5.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.oauth2.create_device_authorization( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.oauth2.create_device_authorization() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_grant(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "appId": "5e5ea5c16897e", - "scopes": [], - "resources": [], - "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", - "prompt": "login", - "redirectUri": "https:\/\/example.com\/callback", - "authTime": 1592981250.0, - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "prompt": "login", + "redirectUri": "https:\/\/example.com\/callback", + "authTime": 1592981250.0, + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.create_grant( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_grant(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "appId": "5e5ea5c16897e", - "scopes": [], - "resources": [], - "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", - "prompt": "login", - "redirectUri": "https:\/\/example.com\/callback", - "authTime": 1592981250.0, - "expire": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "appId": "5e5ea5c16897e", + "scopes": [], + "resources": [], + "authorizationDetails": "[{\"type\":\"calendar\",\"identifier\":\"primary\",\"actions\":[\"read_events\",\"create_event\"]}]", + "prompt": "login", + "redirectUri": "https:\/\/example.com\/callback", + "authTime": 1592981250.0, + "expire": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.get_grant( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_organizations(self, m): data = { - "total": 5.0, - "organizations": [] -} + "total": 5.0, + "organizations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.oauth2.list_organizations( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.oauth2.list_organizations() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_par(self, m): data = { - "request_uri": "urn:appwrite:oauth2:request:5e5ea5c16897e", - "expires_in": 600.0 -} + "request_uri": "urn:appwrite:oauth2:request:5e5ea5c16897e", + "expires_in": 600.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.create_par( '', 'https://example.com', 'code', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_projects(self, m): data = { - "total": 5.0, - "projects": [] -} + "total": 5.0, + "projects": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.oauth2.list_projects( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.oauth2.list_projects() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_reject(self, m): data = { - "redirectUrl": "https:\/\/example.com\/callback?error=access_denied&state=fghij" -} + "redirectUrl": "https:\/\/example.com\/callback?error=access_denied&state=fghij", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.reject( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_revoke(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.revoke( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_token(self, m): data = { - "access_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9...", - "token_type": "Bearer", - "expires_in": 3600.0, - "refresh_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...", - "scope": "openid email profile" -} + "access_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9...", + "token_type": "Bearer", + "expires_in": 3600.0, + "refresh_token": "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9...", + "scope": "openid email profile", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.oauth2.create_token( '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_organization.py b/test/services/test_organization.py index 2bf4dbc8..bb814339 100644 --- a/test/services/test_organization.py +++ b/test/services/test_organization.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.organization import Organization + class OrganizationServiceTest(unittest.TestCase): def setUp(self): @@ -16,792 +17,855 @@ def setUp(self): @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "VIP", - "total": 7.0, - "prefs": {}, - "budgetAlerts": [], - "billingPlan": "tier-1", - "billingPlanId": "tier-1", - "billingPlanDetails": { - "$id": "tier-0", - "name": "Hobby", - "desc": "Hobby plan", - "order": 0.0, - "price": 25, - "trial": 14.0, - "bandwidth": 25.0, - "storage": 25.0, - "imageTransformations": 100.0, - "screenshotsGenerated": 50.0, - "webhooks": 25.0, - "wafRules": 2.0, - "projects": 2.0, - "platforms": 3.0, - "users": 25.0, - "teams": 25.0, - "databases": 25.0, - "databasesReads": 500000.0, - "databasesWrites": 250000.0, - "databasesBatchSize": 100.0, - "buckets": 25.0, - "fileSize": 25.0, - "functions": 25.0, - "sites": 1.0, - "executions": 25.0, - "executionsRetentionCount": 10000.0, - "GBHours": 100.0, - "realtime": 25.0, - "realtimeMessages": 100000.0, - "messages": 1000.0, - "topics": 1.0, - "authPhone": 10.0, - "domains": 5.0, - "usageLogs": 30.0, - "projectInactivityDays": 7.0, - "alertLimit": 80.0, - "usage": { - "bandwidth": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "executions": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "realtime": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "realtimeMessages": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "storage": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + "budgetAlerts": [], + "billingPlan": "tier-1", + "billingPlanId": "tier-1", + "billingPlanDetails": { + "$id": "tier-0", + "name": "Hobby", + "desc": "Hobby plan", + "order": 0.0, + "price": 25, + "trial": 14.0, + "bandwidth": 25.0, + "storage": 25.0, + "imageTransformations": 100.0, + "screenshotsGenerated": 50.0, + "webhooks": 25.0, + "wafRules": 2.0, + "projects": 2.0, + "platforms": 3.0, + "users": 25.0, + "teams": 25.0, + "databases": 25.0, + "databasesReads": 500000.0, + "databasesWrites": 250000.0, + "databasesBatchSize": 100.0, + "buckets": 25.0, + "fileSize": 25.0, + "functions": 25.0, + "sites": 1.0, + "executions": 25.0, + "executionsRetentionCount": 10000.0, + "GBHours": 100.0, + "realtime": 25.0, + "realtimeMessages": 100000.0, + "messages": 1000.0, + "topics": 1.0, + "authPhone": 10.0, + "domains": 5.0, + "usageLogs": 30.0, + "projectInactivityDays": 7.0, + "alertLimit": 80.0, + "usage": { + "bandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "executions": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "realtime": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "realtimeMessages": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "storage": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "users": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "GBHours": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "imageTransformations": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + }, + "addons": {}, + "budgetCapEnabled": True, + "customSmtp": True, + "emailBranding": True, + "requiresPaymentMethod": True, + "requiresBillingAddress": True, + "isAvailable": True, + "selfService": True, + "premiumSupport": True, + "budgeting": True, + "supportsMockNumbers": True, + "supportsOrganizationRoles": True, + "supportsCredits": True, + "supportsDedicatedDatabases": True, + "supportsDisposableEmailValidation": True, + "supportsCanonicalEmailValidation": True, + "supportsFreeEmailValidation": True, + "supportsCorporateEmailValidation": True, + "supportsProjectSpecificRoles": True, + "usagePerProject": True, + "supportedAddons": { + "baa": True, + "premiumGeoDB": True, + "premiumGeoDBOrg": True, + }, + "deploymentSize": 30.0, + "buildSize": 2000.0, + "databasesAllowEncrypt": True, + "group": "pro", + "databaseComputeCredit": 10, }, - "users": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "GBHours": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "imageTransformations": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - } - }, - "addons": {}, - "budgetCapEnabled": True, - "customSmtp": True, - "emailBranding": True, - "requiresPaymentMethod": True, - "requiresBillingAddress": True, - "isAvailable": True, - "selfService": True, - "premiumSupport": True, - "budgeting": True, - "supportsMockNumbers": True, - "supportsOrganizationRoles": True, - "supportsCredits": True, - "supportsDisposableEmailValidation": True, - "supportsCanonicalEmailValidation": True, - "supportsFreeEmailValidation": True, - "supportsCorporateEmailValidation": True, - "supportsProjectSpecificRoles": True, - "usagePerProject": True, - "supportedAddons": { - "baa": True, - "premiumGeoDB": True, - "premiumGeoDBOrg": True - }, - "deploymentSize": 30.0, - "buildSize": 2000.0, - "databasesAllowEncrypt": True, - "group": "pro" - }, - "billingEmail": "billing@org.example", - "billingStartDate": "2020-10-15T06:38:00.000+00:00", - "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingTrialDays": 14.0, - "billingAggregationId": "adbc3de4rddfsd", - "billingInvoiceId": "adbc3de4rddfsd", - "paymentMethodId": "adbc3de4rddfsd", - "status": "active", - "markedForDeletion": True, - "platform": "imagine", - "projects": [] -} + "billingEmail": "billing@org.example", + "billingStartDate": "2020-10-15T06:38:00.000+00:00", + "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialDays": 14.0, + "billingAggregationId": "adbc3de4rddfsd", + "billingInvoiceId": "adbc3de4rddfsd", + "paymentMethodId": "adbc3de4rddfsd", + "status": "active", + "markedForDeletion": True, + "platform": "imagine", + "projects": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.get( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.get() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "VIP", - "total": 7.0, - "prefs": {}, - "budgetAlerts": [], - "billingPlan": "tier-1", - "billingPlanId": "tier-1", - "billingPlanDetails": { - "$id": "tier-0", - "name": "Hobby", - "desc": "Hobby plan", - "order": 0.0, - "price": 25, - "trial": 14.0, - "bandwidth": 25.0, - "storage": 25.0, - "imageTransformations": 100.0, - "screenshotsGenerated": 50.0, - "webhooks": 25.0, - "wafRules": 2.0, - "projects": 2.0, - "platforms": 3.0, - "users": 25.0, - "teams": 25.0, - "databases": 25.0, - "databasesReads": 500000.0, - "databasesWrites": 250000.0, - "databasesBatchSize": 100.0, - "buckets": 25.0, - "fileSize": 25.0, - "functions": 25.0, - "sites": 1.0, - "executions": 25.0, - "executionsRetentionCount": 10000.0, - "GBHours": 100.0, - "realtime": 25.0, - "realtimeMessages": 100000.0, - "messages": 1000.0, - "topics": 1.0, - "authPhone": 10.0, - "domains": 5.0, - "usageLogs": 30.0, - "projectInactivityDays": 7.0, - "alertLimit": 80.0, - "usage": { - "bandwidth": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "executions": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + "budgetAlerts": [], + "billingPlan": "tier-1", + "billingPlanId": "tier-1", + "billingPlanDetails": { + "$id": "tier-0", + "name": "Hobby", + "desc": "Hobby plan", + "order": 0.0, + "price": 25, + "trial": 14.0, + "bandwidth": 25.0, + "storage": 25.0, + "imageTransformations": 100.0, + "screenshotsGenerated": 50.0, + "webhooks": 25.0, + "wafRules": 2.0, + "projects": 2.0, + "platforms": 3.0, + "users": 25.0, + "teams": 25.0, + "databases": 25.0, + "databasesReads": 500000.0, + "databasesWrites": 250000.0, + "databasesBatchSize": 100.0, + "buckets": 25.0, + "fileSize": 25.0, + "functions": 25.0, + "sites": 1.0, + "executions": 25.0, + "executionsRetentionCount": 10000.0, + "GBHours": 100.0, + "realtime": 25.0, + "realtimeMessages": 100000.0, + "messages": 1000.0, + "topics": 1.0, + "authPhone": 10.0, + "domains": 5.0, + "usageLogs": 30.0, + "projectInactivityDays": 7.0, + "alertLimit": 80.0, + "usage": { + "bandwidth": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "executions": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "realtime": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "realtimeMessages": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "storage": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "users": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "GBHours": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + "imageTransformations": { + "name": "", + "unit": "GB", + "currency": "USD", + "price": 5, + "value": 25.0, + "invoiceDesc": "", + }, + }, + "addons": {}, + "budgetCapEnabled": True, + "customSmtp": True, + "emailBranding": True, + "requiresPaymentMethod": True, + "requiresBillingAddress": True, + "isAvailable": True, + "selfService": True, + "premiumSupport": True, + "budgeting": True, + "supportsMockNumbers": True, + "supportsOrganizationRoles": True, + "supportsCredits": True, + "supportsDedicatedDatabases": True, + "supportsDisposableEmailValidation": True, + "supportsCanonicalEmailValidation": True, + "supportsFreeEmailValidation": True, + "supportsCorporateEmailValidation": True, + "supportsProjectSpecificRoles": True, + "usagePerProject": True, + "supportedAddons": { + "baa": True, + "premiumGeoDB": True, + "premiumGeoDBOrg": True, + }, + "deploymentSize": 30.0, + "buildSize": 2000.0, + "databasesAllowEncrypt": True, + "group": "pro", + "databaseComputeCredit": 10, }, - "realtime": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "realtimeMessages": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "storage": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "users": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "GBHours": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - }, - "imageTransformations": { - "name": "", - "unit": "GB", - "currency": "USD", - "price": 5, - "value": 25.0, - "invoiceDesc": "" - } - }, - "addons": {}, - "budgetCapEnabled": True, - "customSmtp": True, - "emailBranding": True, - "requiresPaymentMethod": True, - "requiresBillingAddress": True, - "isAvailable": True, - "selfService": True, - "premiumSupport": True, - "budgeting": True, - "supportsMockNumbers": True, - "supportsOrganizationRoles": True, - "supportsCredits": True, - "supportsDisposableEmailValidation": True, - "supportsCanonicalEmailValidation": True, - "supportsFreeEmailValidation": True, - "supportsCorporateEmailValidation": True, - "supportsProjectSpecificRoles": True, - "usagePerProject": True, - "supportedAddons": { - "baa": True, - "premiumGeoDB": True, - "premiumGeoDBOrg": True - }, - "deploymentSize": 30.0, - "buildSize": 2000.0, - "databasesAllowEncrypt": True, - "group": "pro" - }, - "billingEmail": "billing@org.example", - "billingStartDate": "2020-10-15T06:38:00.000+00:00", - "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", - "billingTrialDays": 14.0, - "billingAggregationId": "adbc3de4rddfsd", - "billingInvoiceId": "adbc3de4rddfsd", - "paymentMethodId": "adbc3de4rddfsd", - "status": "active", - "markedForDeletion": True, - "platform": "imagine", - "projects": [] -} + "billingEmail": "billing@org.example", + "billingStartDate": "2020-10-15T06:38:00.000+00:00", + "billingCurrentInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingNextInvoiceDate": "2020-10-15T06:38:00.000+00:00", + "billingTrialDays": 14.0, + "billingAggregationId": "adbc3de4rddfsd", + "billingInvoiceId": "adbc3de4rddfsd", + "paymentMethodId": "adbc3de4rddfsd", + "status": "active", + "markedForDeletion": True, + "platform": "imagine", + "projects": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.update( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.delete( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.delete() self.assertEqual(response, data) @requests_mock.Mocker() def test_list_installations(self, m): data = { - "total": 5.0, - "installations": [] -} + "total": 5.0, + "installations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.list_installations( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.list_installations() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.create_installation( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.get_installation( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.update_installation( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_installation(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.delete_installation( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_keys(self, m): data = { - "total": 5.0, - "keys": [] -} + "total": 5.0, + "keys": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.list_keys( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.list_keys() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.create_key( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.get_key( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.update_key( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_key(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.delete_key( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_memberships(self, m): data = { - "total": 5.0, - "memberships": [] -} + "total": 5.0, + "memberships": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.list_memberships( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.list_memberships() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.create_membership( [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.get_membership( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.update_membership( '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_membership(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.delete_membership( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_projects(self, m): data = { - "total": 5.0, - "projects": [] -} + "total": 5.0, + "projects": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.organization.list_projects( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.organization.list_projects() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_project(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.create_project( - '', + '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_project(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.get_project( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_project(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.update_project( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_project(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.organization.delete_project( '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_postgresql.py b/test/services/test_postgresql.py new file mode 100644 index 00000000..b255d371 --- /dev/null +++ b/test/services/test_postgresql.py @@ -0,0 +1,1330 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.postgresql import Postgresql + + +class PostgresqlServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.postgresql = Postgresql(self.client) + + @requests_mock.Mocker() + def test_list(self, m): + data = { + "total": 5.0, + "databases": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_specifications() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.delete( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_backups(self, m): + data = { + "total": 5.0, + "backups": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_backups( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_backup( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_backup_policies(self, m): + data = { + "total": 5.0, + "policies": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_backup_policies( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_backup_policy( + '', + '', + '', + '', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_backup_policy(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "Hourly backups", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "services": [], + "resources": [], + "retention": 7.0, + "schedule": "0 * * * *", + "type": "full", + "enabled": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update_backup_policy( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup_policy(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.delete_backup_policy( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_update_backup_storage(self, m): + data = { + "provider": "s3", + "bucket": "my-backup-bucket", + "region": "us-east-1", + "prefix": "backups\/", + "endpoint": "https:\/\/minio.example.com", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update_backup_storage( + '', + 's3', + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_backup(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "policyId": "5e5ea5c16897e", + "trigger": "schedule", + "type": "full", + "requestedType": "incremental", + "fallbackReason": "PostgreSQL incremental backups are not offered because they cannot be restored: archived WAL is physical and cannot replay onto a logically-restored base. A full backup was taken instead; use a point-in-time restore (targetTime) to recover to a moment between fulls.", + "status": "completed", + "sizeBytes": 1073741824.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_backup( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_backup(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.delete_backup( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_branches(self, m): + data = { + "total": 2.0, + "branches": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_branches( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_branch( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_branch(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.delete_branch( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_credentials(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update_credentials( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_execution(self, m): + data = { + "rows": [], + "rowCount": 1.0, + "columns": [], + "durationMs": 12.0, + "truncated": True, + "bytes": 1024.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_execution( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_extensions(self, m): + data = { + "installed": [], + "available": [], + "metadata": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_extensions( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_extension(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_extension( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_extension(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.delete_extension( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_failover( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_maintenance(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update_maintenance( + '', + 'sun', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_migration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_migration( + '', + 'shared', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_pitr(self, m): + data = { + "earliest": "2020-10-15T06:38:00.000+00:00", + "latest": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_pitr( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_pooler(self, m): + data = { + "enabled": True, + "mode": "transaction", + "maxConnections": 200.0, + "defaultPoolSize": 25.0, + "port": 6432.0, + "readWriteSplitting": True, + "poolerCpuRequest": "100m", + "poolerCpuLimit": "200m", + "poolerMemoryRequest": "64Mi", + "poolerMemoryLimit": "128Mi", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_pooler( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_pooler(self, m): + data = { + "enabled": True, + "mode": "transaction", + "maxConnections": 200.0, + "defaultPoolSize": 25.0, + "port": 6432.0, + "readWriteSplitting": True, + "poolerCpuRequest": "100m", + "poolerCpuLimit": "200m", + "poolerMemoryRequest": "64Mi", + "poolerMemoryLimit": "128Mi", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.update_pooler( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_replicas( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_restorations(self, m): + data = { + "total": 5.0, + "restorations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.list_restorations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_restoration( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_restoration(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "databaseId": "5e5ea5c16897e", + "sourceDatabaseId": "5e5ea5c16897e", + "projectId": "5e5ea5c16897e", + "backupId": "5e5ea5c16897e", + "type": "backup", + "status": "completed", + "targetTime": "2020-10-15T06:38:00.000+00:00", + "startedAt": "2020-10-15T06:38:00.000+00:00", + "completedAt": "2020-10-15T06:38:00.000+00:00", + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_restoration( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.get_status( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_upgrade(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.postgresql.create_upgrade( + '', + '', + ) + self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_presences.py b/test/services/test_presences.py index c5b3189a..709ebb15 100644 --- a/test/services/test_presences.py +++ b/test/services/test_presences.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.presences import Presences + class PresencesServiceTest(unittest.TestCase): def setUp(self): @@ -16,86 +17,99 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "presences": [] -} + "total": 5.0, + "presences": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.presences.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.presences.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "userId": "674af8f3e12a5f9ac0be", - "source": "HTTP" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "userId": "674af8f3e12a5f9ac0be", + "source": "HTTP", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.presences.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_upsert(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "userId": "674af8f3e12a5f9ac0be", - "source": "HTTP" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "userId": "674af8f3e12a5f9ac0be", + "source": "HTTP", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.presences.upsert( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "userId": "674af8f3e12a5f9ac0be", - "source": "HTTP" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "userId": "674af8f3e12a5f9ac0be", + "source": "HTTP", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.presences.update( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.presences.delete( '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_project.py b/test/services/test_project.py index 9f8f36e0..6ad83c58 100644 --- a/test/services/test_project.py +++ b/test/services/test_project.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.project import Project + class ProjectServiceTest(unittest.TestCase): def setUp(self): @@ -16,2243 +17,2489 @@ def setUp(self): @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.get( - ) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.project.get() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.delete( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.delete() self.assertEqual(response, data) @requests_mock.Mocker() def test_update_auth_method(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_auth_method( 'email-password', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_keys(self, m): data = { - "total": 5.0, - "keys": [] -} + "total": 5.0, + "keys": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_keys( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_keys() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_ephemeral_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_ephemeral_key( [], 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_key( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_key(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My API Key", - "expire": "2020-10-15T06:38:00.000+00:00", - "scopes": [], - "secret": "919c2d18fb5d4...a2ae413da83346ad2", - "accessedAt": "2020-10-15T06:38:00.000+00:00", - "sdks": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My API Key", + "expire": "2020-10-15T06:38:00.000+00:00", + "scopes": [], + "secret": "919c2d18fb5d4...a2ae413da83346ad2", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + "sdks": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_key( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_key(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.delete_key( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_labels(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_labels( [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_mock_phones(self, m): data = { - "total": 5.0, - "mockNumbers": [] -} + "total": 5.0, + "mockNumbers": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_mock_phones( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_mock_phones() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mock_phone(self, m): data = { - "number": "+1612842323", - "otp": "123456", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} + "number": "+1612842323", + "otp": "123456", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_mock_phone( '+12065550100', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_mock_phone(self, m): data = { - "number": "+1612842323", - "otp": "123456", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} + "number": "+1612842323", + "otp": "123456", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_mock_phone( '+12065550100', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mock_phone(self, m): data = { - "number": "+1612842323", - "otp": "123456", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} + "number": "+1612842323", + "otp": "123456", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_mock_phone( '+12065550100', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_mock_phone(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.delete_mock_phone( '+12065550100', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_o_auth2_providers(self, m): data = { - "total": 5.0, - "providers": [] -} + "total": 5.0, + "providers": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_o_auth2_providers( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_o_auth2_providers() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_server(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_o_auth2_server( True, 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_amazon(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "amzn1.application-oa2-client.87400c00000000000000000000063d5b2", - "clientSecret": "79ffe4000000000000000000000000000000000000000000000000000002de55" -} + "$id": "github", + "enabled": True, + "clientId": "amzn1.application-oa2-client.87400c00000000000000000000063d5b2", + "clientSecret": "79ffe4000000000000000000000000000000000000000000000000000002de55", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_amazon( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_amazon() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_apple(self, m): data = { - "$id": "apple", - "enabled": True, - "serviceId": "ip.appwrite.app.web", - "keyId": "P4000000N8", - "teamId": "D4000000R6", - "p8File": "-----BEGIN PRIVATE KEY-----MIGTAg...jy2Xbna-----END PRIVATE KEY-----" -} + "$id": "apple", + "enabled": True, + "serviceId": "ip.appwrite.app.web", + "keyId": "P4000000N8", + "teamId": "D4000000R6", + "p8File": "-----BEGIN PRIVATE KEY-----MIGTAg...jy2Xbna-----END PRIVATE KEY-----", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_apple( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_apple() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_appwrite(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "6a42000000000000b5a0", - "clientSecret": "b86afd000000000000000000000000000000000000000000000000000ced5f93" -} + "$id": "github", + "enabled": True, + "clientId": "6a42000000000000b5a0", + "clientSecret": "b86afd000000000000000000000000000000000000000000000000000ced5f93", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_appwrite( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_appwrite() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_auth0(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "OaOkIA000000000000000000005KLSYq", - "clientSecret": "zXz0000-00000000000000000000000000000-00000000000000000000PJafnF", - "endpoint": "example.us.auth0.com" -} + "$id": "github", + "enabled": True, + "clientId": "OaOkIA000000000000000000005KLSYq", + "clientSecret": "zXz0000-00000000000000000000000000000-00000000000000000000PJafnF", + "endpoint": "example.us.auth0.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_auth0( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_auth0() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_authentik(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "dTKOPa0000000000000000000000000000e7G8hv", - "clientSecret": "ntQadq000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000Hp5WK", - "endpoint": "example.authentik.com" -} + "$id": "github", + "enabled": True, + "clientId": "dTKOPa0000000000000000000000000000e7G8hv", + "clientSecret": "ntQadq000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000Hp5WK", + "endpoint": "example.authentik.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_authentik( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_authentik() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_autodesk(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "5zw90v00000000000000000000kVYXN7", - "clientSecret": "7I000000000000MW" -} + "$id": "github", + "enabled": True, + "clientId": "5zw90v00000000000000000000kVYXN7", + "clientSecret": "7I000000000000MW", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_autodesk( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_autodesk() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_bitbucket(self, m): data = { - "$id": "github", - "enabled": True, - "key": "Knt70000000000ByRc", - "secret": "NMfLZJ00000000000000000000TLQdDx" -} + "$id": "github", + "enabled": True, + "key": "Knt70000000000ByRc", + "secret": "NMfLZJ00000000000000000000TLQdDx", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_bitbucket( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_bitbucket() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_bitly(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "d95151000000000000000000000000000067af9b", - "clientSecret": "a13e250000000000000000000000000000d73095" -} + "$id": "github", + "enabled": True, + "clientId": "d95151000000000000000000000000000067af9b", + "clientSecret": "a13e250000000000000000000000000000d73095", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_bitly( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_bitly() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_box(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "deglcs00000000000000000000x2og6y", - "clientSecret": "OKM1f100000000000000000000eshEif" -} + "$id": "github", + "enabled": True, + "clientId": "deglcs00000000000000000000x2og6y", + "clientSecret": "OKM1f100000000000000000000eshEif", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_box( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_box() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_dailymotion(self, m): data = { - "$id": "github", - "enabled": True, - "apiKey": "07a9000000000000067f", - "apiSecret": "a399a90000000000000000000000000000d90639" -} + "$id": "github", + "enabled": True, + "apiKey": "07a9000000000000067f", + "apiSecret": "a399a90000000000000000000000000000d90639", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_dailymotion( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_dailymotion() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_discord(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "950722000000343754", - "clientSecret": "YmPXnM000000000000000000002zFg5D" -} + "$id": "github", + "enabled": True, + "clientId": "950722000000343754", + "clientSecret": "YmPXnM000000000000000000002zFg5D", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_discord( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_discord() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_disqus(self, m): data = { - "$id": "github", - "enabled": True, - "publicKey": "cgegH70000000000000000000000000000000000000000000000000000Hr1nYX", - "secretKey": "W7Bykj00000000000000000000000000000000000000000000000000003o43w9" -} + "$id": "github", + "enabled": True, + "publicKey": "cgegH70000000000000000000000000000000000000000000000000000Hr1nYX", + "secretKey": "W7Bykj00000000000000000000000000000000000000000000000000003o43w9", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_disqus( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_disqus() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_dropbox(self, m): data = { - "$id": "github", - "enabled": True, - "appKey": "jl000000000009t", - "appSecret": "g200000000000vw" -} + "$id": "github", + "enabled": True, + "appKey": "jl000000000009t", + "appSecret": "g200000000000vw", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_dropbox( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_dropbox() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_etsy(self, m): data = { - "$id": "github", - "enabled": True, - "keyString": "nsgzxh0000000000008j85a2", - "sharedSecret": "tp000000ru" -} + "$id": "github", + "enabled": True, + "keyString": "nsgzxh0000000000008j85a2", + "sharedSecret": "tp000000ru", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_etsy( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_etsy() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_facebook(self, m): data = { - "$id": "github", - "enabled": True, - "appId": "260600000007694", - "appSecret": "2d0b2800000000000000000000d38af4" -} + "$id": "github", + "enabled": True, + "appId": "260600000007694", + "appSecret": "2d0b2800000000000000000000d38af4", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_facebook( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_facebook() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_figma(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "byay5H0000000000VtiI40", - "clientSecret": "yEpOYn0000000000000000004iIsU5" -} + "$id": "github", + "enabled": True, + "clientId": "byay5H0000000000VtiI40", + "clientSecret": "yEpOYn0000000000000000004iIsU5", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_figma( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_figma() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_fusion_auth(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "b2222c00-0000-0000-0000-000000862097", - "clientSecret": "Jx4s0C0000000000000000000000000000000wGqLsc", - "endpoint": "example.fusionauth.io" -} + "$id": "github", + "enabled": True, + "clientId": "b2222c00-0000-0000-0000-000000862097", + "clientSecret": "Jx4s0C0000000000000000000000000000000wGqLsc", + "endpoint": "example.fusionauth.io", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_fusion_auth( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_fusion_auth() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_git_hub(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "e4d87900000000540733", - "clientSecret": "5e07c00000000000000000000000000000198bcc" -} + "$id": "github", + "enabled": True, + "clientId": "e4d87900000000540733", + "clientSecret": "5e07c00000000000000000000000000000198bcc", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_git_hub( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_git_hub() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_gitlab(self, m): data = { - "$id": "github", - "enabled": True, - "applicationId": "d41ffe0000000000000000000000000000000000000000000000000000d5e252", - "secret": "gloas-838cfa0000000000000000000000000000000000000000000000000000ecbb38", - "endpoint": "https:\/\/gitlab.com" -} + "$id": "github", + "enabled": True, + "applicationId": "d41ffe0000000000000000000000000000000000000000000000000000d5e252", + "secret": "gloas-838cfa0000000000000000000000000000000000000000000000000000ecbb38", + "endpoint": "https:\/\/gitlab.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_gitlab( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_gitlab() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_google(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "120000000095-92ifjb00000000000000000000g7ijfb.apps.googleusercontent.com", - "clientSecret": "GOCSPX-2k8gsR0000000000000000VNahJj", - "prompt": [] -} + "$id": "github", + "enabled": True, + "clientId": "120000000095-92ifjb00000000000000000000g7ijfb.apps.googleusercontent.com", + "clientSecret": "GOCSPX-2k8gsR0000000000000000VNahJj", + "prompt": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_google( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) + response = self.project.update_o_auth2_google() + self.assertEqual(response.to_dict(), data) + @requests_mock.Mocker() + def test_update_o_auth2_hugging_face(self, m): + data = { + "$id": "github", + "enabled": True, + "clientId": "2ab9cff9-d711-40ad-a91e-b08a49c42d24", + "clientSecret": "oauth_app_secret_wcLhRtl000000000000000000000xbNdLt", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.project.update_o_auth2_hugging_face() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_keycloak(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "appwrite-o0000000st-app", - "clientSecret": "jdjrJd00000000000000000000HUsaZO", - "endpoint": "keycloak.example.com", - "realmName": "appwrite-realm" -} + "$id": "github", + "enabled": True, + "clientId": "appwrite-o0000000st-app", + "clientSecret": "jdjrJd00000000000000000000HUsaZO", + "endpoint": "keycloak.example.com", + "realmName": "appwrite-realm", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_keycloak( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_keycloak() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_kick(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "01KQ7C00000000000001MFHS32", - "clientSecret": "34ac5600000000000000000000000000000000000000000000000000e830c8b" -} + "$id": "github", + "enabled": True, + "clientId": "01KQ7C00000000000001MFHS32", + "clientSecret": "34ac5600000000000000000000000000000000000000000000000000e830c8b", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_kick( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_kick() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_linkedin(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "770000000000dv", - "primaryClientSecret": "WPL_AP1.2Bf0000000000000.\/HtlYw==" -} + "$id": "github", + "enabled": True, + "clientId": "770000000000dv", + "primaryClientSecret": "WPL_AP1.2Bf0000000000000.\/HtlYw==", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_linkedin( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_linkedin() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_microsoft(self, m): data = { - "$id": "github", - "enabled": True, - "applicationId": "00001111-aaaa-2222-bbbb-3333cccc4444", - "applicationSecret": "A1bC2dE3fH4iJ5kL6mN7oP8qR9sT0u", - "tenant": "common" -} + "$id": "github", + "enabled": True, + "applicationId": "00001111-aaaa-2222-bbbb-3333cccc4444", + "applicationSecret": "A1bC2dE3fH4iJ5kL6mN7oP8qR9sT0u", + "tenant": "common", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_microsoft( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_microsoft() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_notion(self, m): data = { - "$id": "github", - "enabled": True, - "oauthClientId": "341d8700-0000-0000-0000-000000446ee3", - "oauthClientSecret": "secret_dLUr4b000000000000000000000000000000lFHAa9" -} + "$id": "github", + "enabled": True, + "oauthClientId": "341d8700-0000-0000-0000-000000446ee3", + "oauthClientSecret": "secret_dLUr4b000000000000000000000000000000lFHAa9", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_notion( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_notion() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_oidc(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "qibI2x0000000000000000000000000006L2YFoG", - "clientSecret": "Ah68ed000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003qpcHV", - "wellKnownURL": "https:\/\/myoauth.com\/.well-known\/openid-configuration", - "authorizationURL": "https:\/\/myoauth.com\/oauth2\/authorize", - "tokenURL": "https:\/\/myoauth.com\/oauth2\/token", - "userInfoURL": "https:\/\/myoauth.com\/oauth2\/userinfo", - "prompt": [] -} + "$id": "github", + "enabled": True, + "clientId": "qibI2x0000000000000000000000000006L2YFoG", + "clientSecret": "Ah68ed000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003qpcHV", + "wellKnownURL": "https:\/\/myoauth.com\/.well-known\/openid-configuration", + "authorizationURL": "https:\/\/myoauth.com\/oauth2\/authorize", + "tokenURL": "https:\/\/myoauth.com\/oauth2\/token", + "userInfoURL": "https:\/\/myoauth.com\/oauth2\/userinfo", + "prompt": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_oidc( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_oidc() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_okta(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "0oa00000000000000698", - "clientSecret": "Kiq0000000000000000000000000000000000000-00000000000H2L5-3SJ-vRV", - "domain": "trial-6400025.okta.com", - "authorizationServerId": "aus000000000000000h7z" -} + "$id": "github", + "enabled": True, + "clientId": "0oa00000000000000698", + "clientSecret": "Kiq0000000000000000000000000000000000000-00000000000H2L5-3SJ-vRV", + "domain": "trial-6400025.okta.com", + "authorizationServerId": "aus000000000000000h7z", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_okta( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_okta() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_paypal(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "AdhIEG7-000000000000-0000000000000000000000000000000-0000000000000000000000-2pyB", - "secretKey": "EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp" -} + "$id": "github", + "enabled": True, + "clientId": "AdhIEG7-000000000000-0000000000000000000000000000000-0000000000000000000000-2pyB", + "secretKey": "EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_paypal( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_paypal() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_paypal_sandbox(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "AdhIEG7-000000000000-0000000000000000000000000000000-0000000000000000000000-2pyB", - "secretKey": "EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp" -} + "$id": "github", + "enabled": True, + "clientId": "AdhIEG7-000000000000-0000000000000000000000000000000-0000000000000000000000-2pyB", + "secretKey": "EH8KCXtew--000000000000000000000000000000000000000_C-1_5UP_000000000000000CB7KDp", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_paypal_sandbox( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_paypal_sandbox() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_podio(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "appwrite-oauth-test-app", - "clientSecret": "Rn247T0000000000000000000000000000000000000000000000000000W2zWTN" -} + "$id": "github", + "enabled": True, + "clientId": "appwrite-oauth-test-app", + "clientSecret": "Rn247T0000000000000000000000000000000000000000000000000000W2zWTN", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_podio( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_podio() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_salesforce(self, m): data = { - "$id": "github", - "enabled": True, - "customerKey": "3MVG9I0000000000000000000000000000000000000000000000000000000000000000000000000C5Aejq", - "customerSecret": "3w000000000000e2" -} + "$id": "github", + "enabled": True, + "customerKey": "3MVG9I0000000000000000000000000000000000000000000000000000000000000000000000000C5Aejq", + "customerSecret": "3w000000000000e2", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_salesforce( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_salesforce() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_slack(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "23000000089.15000000000023", - "clientSecret": "81656000000000000000000000f3d2fd" -} + "$id": "github", + "enabled": True, + "clientId": "23000000089.15000000000023", + "clientSecret": "81656000000000000000000000f3d2fd", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_slack( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_slack() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_spotify(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "6ec271000000000000000000009beace", - "clientSecret": "db068a000000000000000000008b5b9f" -} + "$id": "github", + "enabled": True, + "clientId": "6ec271000000000000000000009beace", + "clientSecret": "db068a000000000000000000008b5b9f", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_spotify( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_spotify() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_stripe(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "ca_UKibXX0000000000000000000006byvR", - "apiSecretKey": "sk_51SfOd000000000000000000000000000000000000000000000000000000000000000000000000000000000000000QGWYfp" -} + "$id": "github", + "enabled": True, + "clientId": "ca_UKibXX0000000000000000000006byvR", + "apiSecretKey": "sk_51SfOd000000000000000000000000000000000000000000000000000000000000000000000000000000000000000QGWYfp", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_stripe( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_stripe() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_tradeshift(self, m): data = { - "$id": "github", - "enabled": True, - "oauth2ClientId": "appwrite-test-org.appwrite-test-app", - "oauth2ClientSecret": "7cb52700-0000-0000-0000-000000ca5b83" -} + "$id": "github", + "enabled": True, + "oauth2ClientId": "appwrite-test-org.appwrite-test-app", + "oauth2ClientSecret": "7cb52700-0000-0000-0000-000000ca5b83", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_tradeshift( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_tradeshift() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_tradeshift_sandbox(self, m): data = { - "$id": "github", - "enabled": True, - "oauth2ClientId": "appwrite-test-org.appwrite-test-app", - "oauth2ClientSecret": "7cb52700-0000-0000-0000-000000ca5b83" -} + "$id": "github", + "enabled": True, + "oauth2ClientId": "appwrite-test-org.appwrite-test-app", + "oauth2ClientSecret": "7cb52700-0000-0000-0000-000000ca5b83", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_tradeshift_sandbox( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_tradeshift_sandbox() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_twitch(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "vvi0in000000000000000000ikmt9p", - "clientSecret": "pmapue000000000000000000zylw3v" -} + "$id": "github", + "enabled": True, + "clientId": "vvi0in000000000000000000ikmt9p", + "clientSecret": "pmapue000000000000000000zylw3v", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_twitch( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_twitch() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_word_press(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "130005", - "clientSecret": "PlBfJS0000000000000000000000000000000000000000000000000000EdUZJk" -} + "$id": "github", + "enabled": True, + "clientId": "130005", + "clientSecret": "PlBfJS0000000000000000000000000000000000000000000000000000EdUZJk", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_word_press( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_word_press() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_x(self, m): data = { - "$id": "github", - "enabled": True, - "customerKey": "slzZV0000000000000NFLaWT", - "secretKey": "tkEPkp00000000000000000000000000000000000000FTxbI9" -} + "$id": "github", + "enabled": True, + "customerKey": "slzZV0000000000000NFLaWT", + "secretKey": "tkEPkp00000000000000000000000000000000000000FTxbI9", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_x( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_x() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_yahoo(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "dj0yJm000000000000000000000000000000000000000000000000000000000000000000000000000000000000Z4PWRm", - "clientSecret": "cf978f0000000000000000000000000000c5e2e9" -} + "$id": "github", + "enabled": True, + "clientId": "dj0yJm000000000000000000000000000000000000000000000000000000000000000000000000000000000000Z4PWRm", + "clientSecret": "cf978f0000000000000000000000000000c5e2e9", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_yahoo( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_yahoo() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_yandex(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "6a8a6a0000000000000000000091483c", - "clientSecret": "bbf98500000000000000000000c75a63" -} + "$id": "github", + "enabled": True, + "clientId": "6a8a6a0000000000000000000091483c", + "clientSecret": "bbf98500000000000000000000c75a63", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_yandex( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_yandex() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_zoho(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "1000.83C178000000000000000000RPNX0B", - "clientSecret": "fb5cac000000000000000000000000000000a68f6e" -} + "$id": "github", + "enabled": True, + "clientId": "1000.83C178000000000000000000RPNX0B", + "clientSecret": "fb5cac000000000000000000000000000000a68f6e", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_zoho( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_zoho() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_o_auth2_zoom(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "QMAC00000000000000w0AQ", - "clientSecret": "GAWsG4000000000000000000007U01ON" -} + "$id": "github", + "enabled": True, + "clientId": "QMAC00000000000000w0AQ", + "clientSecret": "GAWsG4000000000000000000007U01ON", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_o_auth2_zoom( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_o_auth2_zoom() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_o_auth2_provider(self, m): data = { - "$id": "github", - "enabled": True, - "clientId": "e4d87900000000540733", - "clientSecret": "5e07c00000000000000000000000000000198bcc" -} + "$id": "github", + "enabled": True, + "clientId": "e4d87900000000540733", + "clientSecret": "5e07c00000000000000000000000000000198bcc", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_o_auth2_provider( 'amazon', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_platforms(self, m): data = { - "total": 5.0, - "platforms": [] -} + "total": 5.0, + "platforms": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_platforms( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_platforms() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_android_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "applicationId": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "applicationId": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_android_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_android_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "applicationId": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "applicationId": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_android_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_apple_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "bundleIdentifier": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "bundleIdentifier": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_apple_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_apple_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "bundleIdentifier": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "bundleIdentifier": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_apple_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_linux_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "packageName": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "packageName": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_linux_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_linux_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "packageName": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "packageName": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_linux_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_web_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "hostname": "app.example.com" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "hostname": "app.example.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_web_platform( '', '', 'app.example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_web_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "hostname": "app.example.com" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "hostname": "app.example.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_web_platform( '', '', 'app.example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_windows_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "packageIdentifierName": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "packageIdentifierName": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_windows_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_windows_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "packageIdentifierName": "com.company.appname" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "packageIdentifierName": "com.company.appname", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_windows_platform( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_platform(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Web App", - "type": "web", - "hostname": "app.example.com" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Web App", + "type": "web", + "hostname": "app.example.com", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_platform( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_platform(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.delete_platform( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_policies(self, m): data = { - "total": 10.0, - "policies": [] -} + "total": 10.0, + "policies": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_policies( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_policies() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_deny_aliased_email_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_deny_aliased_email_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_deny_corporate_email_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_deny_corporate_email_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_deny_disposable_email_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_deny_disposable_email_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_deny_free_email_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_deny_free_email_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_membership_privacy_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_membership_privacy_policy( - ) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.project.update_membership_privacy_policy() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_factors_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_mfa_factors_policy( - ) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.project.update_mfa_factors_policy() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password_dictionary_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_password_dictionary_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password_history_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_password_history_policy( 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password_personal_data_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_password_personal_data_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password_strength_policy(self, m): data = { - "$id": "password-dictionary", - "min": 12.0, - "uppercase": True, - "lowercase": True, - "number": True, - "symbols": True -} + "$id": "password-dictionary", + "min": 12.0, + "uppercase": True, + "lowercase": True, + "number": True, + "symbols": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_password_strength_policy( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.update_password_strength_policy() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_session_alert_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_session_alert_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_session_duration_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_session_duration_policy( 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_session_invalidation_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_session_invalidation_policy( True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_session_limit_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_session_limit_policy( 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_user_limit_policy(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_user_limit_policy( 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_policy(self, m): data = { - "$id": "password-dictionary", - "enabled": True -} + "$id": "password-dictionary", + "enabled": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_policy( 'password-dictionary', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_protocol(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_protocol( 'rest', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_service(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_service( 'account', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_smtp(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "New Project", - "teamId": "1592981250", - "region": "fra", - "devKeys": [], - "smtpEnabled": True, - "smtpSenderName": "John Appwrite", - "smtpSenderEmail": "john@appwrite.io", - "smtpReplyToName": "Support Team", - "smtpReplyToEmail": "support@appwrite.io", - "smtpHost": "mail.appwrite.io", - "smtpPort": 25.0, - "smtpUsername": "emailuser", - "smtpPassword": "smtp-password", - "smtpSecure": "tls", - "pingCount": 1.0, - "pingedAt": "2020-10-15T06:38:00.000+00:00", - "labels": [], - "status": "active", - "onboarding": {}, - "authMethods": [], - "services": [], - "protocols": [], - "blocks": [], - "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", - "wafEnabled": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.update_smtp( - ) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "New Project", + "teamId": "1592981250", + "region": "fra", + "devKeys": [], + "smtpEnabled": True, + "smtpSenderName": "John Appwrite", + "smtpSenderEmail": "john@appwrite.io", + "smtpReplyToName": "Support Team", + "smtpReplyToEmail": "support@appwrite.io", + "smtpHost": "mail.appwrite.io", + "smtpPort": 25.0, + "smtpUsername": "emailuser", + "smtpPassword": "smtp-password", + "smtpSecure": "tls", + "pingCount": 1.0, + "pingedAt": "2020-10-15T06:38:00.000+00:00", + "labels": [], + "status": "active", + "onboarding": {}, + "authMethods": [], + "services": [], + "protocols": [], + "blocks": [], + "consoleAccessedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.project.update_smtp() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_smtp_test(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_smtp_test( [], ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_email_templates(self, m): data = { - "total": 5.0, - "templates": [] -} + "total": 5.0, + "templates": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_email_templates( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_email_templates() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email_template(self, m): data = { - "templateId": "verification", - "locale": "en_us", - "message": "Click on the link to verify your account.", - "senderName": "My User", - "senderEmail": "mail@appwrite.io", - "replyToEmail": "emails@appwrite.io", - "replyToName": "Support Team", - "subject": "Please verify your email address" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "templateId": "verification", + "locale": "en_us", + "message": "Click on the link to verify your account.", + "senderName": "My User", + "senderEmail": "mail@appwrite.io", + "replyToEmail": "emails@appwrite.io", + "replyToName": "Support Team", + "subject": "Please verify your email address", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_email_template( 'verification', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_email_template(self, m): data = { - "templateId": "verification", - "locale": "en_us", - "message": "Click on the link to verify your account.", - "senderName": "My User", - "senderEmail": "mail@appwrite.io", - "replyToEmail": "emails@appwrite.io", - "replyToName": "Support Team", - "subject": "Please verify your email address" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "templateId": "verification", + "locale": "en_us", + "message": "Click on the link to verify your account.", + "senderName": "My User", + "senderEmail": "mail@appwrite.io", + "replyToEmail": "emails@appwrite.io", + "replyToName": "Support Team", + "subject": "Please verify your email address", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_email_template( 'verification', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_variables(self, m): data = { - "total": 5.0, - "variables": [] -} + "total": 5.0, + "variables": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.project.list_variables( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.project.list_variables() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.create_variable( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.get_variable( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.update_variable( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_variable(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.project.delete_variable( '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_proxy.py b/test/services/test_proxy.py index 0891cc85..ad5543f8 100644 --- a/test/services/test_proxy.py +++ b/test/services/test_proxy.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.proxy import Proxy + class ProxyServiceTest(unittest.TestCase): def setUp(self): @@ -16,212 +17,237 @@ def setUp(self): @requests_mock.Mocker() def test_create_invalidation(self, m): data = { - "domain": "appwrite.company.com", - "type": "tag", - "reference": "products", - "status": "success" -} + "domain": "appwrite.company.com", + "type": "tag", + "reference": "products", + "status": "success", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.create_invalidation( - '', + 'example.com', 'tag', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_rules(self, m): data = { - "total": 5.0, - "rules": [] -} + "total": 5.0, + "rules": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.proxy.list_rules( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.proxy.list_rules() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_api_rule(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.create_api_rule( - '', + 'example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_function_rule(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.create_function_rule( - '', + 'example.com', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_redirect_rule(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.create_redirect_rule( - '', + 'example.com', 'https://example.com', '301', '', 'site', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_site_rule(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.create_site_rule( - '', + 'example.com', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_rule(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.get_rule( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_rule(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.delete_rule( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_rule_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "domain": "appwrite.company.com", - "type": "deployment", - "trigger": "manual", - "redirectUrl": "https:\/\/appwrite.io\/docs", - "redirectStatusCode": 301.0, - "deploymentId": "n3u9feiwmf", - "deploymentResourceId": "n3u9feiwmf", - "deploymentVcsProviderBranch": "main", - "status": "verified", - "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", - "renewAt": "datetime" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "domain": "appwrite.company.com", + "type": "deployment", + "trigger": "manual", + "redirectUrl": "https:\/\/appwrite.io\/docs", + "redirectStatusCode": 301.0, + "deploymentId": "n3u9feiwmf", + "deploymentResourceId": "n3u9feiwmf", + "deploymentVcsProviderBranch": "main", + "status": "verified", + "logs": "Verification of DNS records failed with DNS resolver 8.8.8.8. Domain stage.myapp.com does not have DNS record.", + "renewAt": "datetime", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.proxy.update_rule_status( '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_sites.py b/test/services/test_sites.py index e514bfc3..f8271b9f 100644 --- a/test/services/test_sites.py +++ b/test/services/test_sites.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.sites import Sites + class SitesServiceTest(unittest.TestCase): def setUp(self): @@ -16,382 +17,420 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "sites": [] -} + "total": 5.0, + "sites": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.sites.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.sites.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Site", - "enabled": True, - "live": True, - "logging": True, - "framework": "react", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "deploymentScreenshotLight": "5e5ea5c16897e", - "deploymentScreenshotDark": "5e5ea5c16897e", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "vars": [], - "timeout": 300.0, - "installCommand": "npm install", - "buildCommand": "npm run build", - "startCommand": "node custom-server.mjs", - "outputDirectory": "build", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "sites\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb", - "buildRuntime": "node-22", - "adapter": "static", - "fallbackFile": "index.html" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Site", + "enabled": True, + "live": True, + "logging": True, + "framework": "react", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "deploymentScreenshotLight": "5e5ea5c16897e", + "deploymentScreenshotDark": "5e5ea5c16897e", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "timeout": 300.0, + "installCommand": "npm install", + "buildCommand": "npm run build", + "startCommand": "node custom-server.mjs", + "outputDirectory": "build", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "sites\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + "buildRuntime": "node-22", + "adapter": "static", + "fallbackFile": "index.html", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create( '', '', 'analog', 'node-14.5', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_frameworks(self, m): data = { - "total": 5.0, - "frameworks": [] -} + "total": 5.0, + "frameworks": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.sites.list_frameworks( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.sites.list_frameworks() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_specifications(self, m): data = { - "total": 5.0, - "specifications": [] -} + "total": 5.0, + "specifications": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.sites.list_specifications( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.sites.list_specifications() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Site", - "enabled": True, - "live": True, - "logging": True, - "framework": "react", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "deploymentScreenshotLight": "5e5ea5c16897e", - "deploymentScreenshotDark": "5e5ea5c16897e", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "vars": [], - "timeout": 300.0, - "installCommand": "npm install", - "buildCommand": "npm run build", - "startCommand": "node custom-server.mjs", - "outputDirectory": "build", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "sites\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb", - "buildRuntime": "node-22", - "adapter": "static", - "fallbackFile": "index.html" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Site", + "enabled": True, + "live": True, + "logging": True, + "framework": "react", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "deploymentScreenshotLight": "5e5ea5c16897e", + "deploymentScreenshotDark": "5e5ea5c16897e", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "timeout": 300.0, + "installCommand": "npm install", + "buildCommand": "npm run build", + "startCommand": "node custom-server.mjs", + "outputDirectory": "build", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "sites\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + "buildRuntime": "node-22", + "adapter": "static", + "fallbackFile": "index.html", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Site", - "enabled": True, - "live": True, - "logging": True, - "framework": "react", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "deploymentScreenshotLight": "5e5ea5c16897e", - "deploymentScreenshotDark": "5e5ea5c16897e", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "vars": [], - "timeout": 300.0, - "installCommand": "npm install", - "buildCommand": "npm run build", - "startCommand": "node custom-server.mjs", - "outputDirectory": "build", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "sites\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb", - "buildRuntime": "node-22", - "adapter": "static", - "fallbackFile": "index.html" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Site", + "enabled": True, + "live": True, + "logging": True, + "framework": "react", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "deploymentScreenshotLight": "5e5ea5c16897e", + "deploymentScreenshotDark": "5e5ea5c16897e", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "timeout": 300.0, + "installCommand": "npm install", + "buildCommand": "npm run build", + "startCommand": "node custom-server.mjs", + "outputDirectory": "build", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "sites\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + "buildRuntime": "node-22", + "adapter": "static", + "fallbackFile": "index.html", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.update( '', '', 'analog', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_site_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Site", - "enabled": True, - "live": True, - "logging": True, - "framework": "react", - "deploymentRetention": 7.0, - "deploymentId": "5e5ea5c16897e", - "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "deploymentScreenshotLight": "5e5ea5c16897e", - "deploymentScreenshotDark": "5e5ea5c16897e", - "latestDeploymentId": "5e5ea5c16897e", - "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", - "latestDeploymentStatus": "ready", - "vars": [], - "timeout": 300.0, - "installCommand": "npm install", - "buildCommand": "npm run build", - "startCommand": "node custom-server.mjs", - "outputDirectory": "build", - "installationId": "6m40at4ejk5h2u9s1hboo", - "providerRepositoryId": "appwrite", - "providerBranch": "main", - "providerRootDirectory": "sites\/helloWorld", - "providerSilentMode": True, - "providerBranches": [], - "providerPaths": [], - "buildSpecification": "s-1vcpu-512mb", - "runtimeSpecification": "s-1vcpu-512mb", - "buildRuntime": "node-22", - "adapter": "static", - "fallbackFile": "index.html" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Site", + "enabled": True, + "live": True, + "logging": True, + "framework": "react", + "deploymentRetention": 7.0, + "deploymentId": "5e5ea5c16897e", + "deploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "deploymentScreenshotLight": "5e5ea5c16897e", + "deploymentScreenshotDark": "5e5ea5c16897e", + "latestDeploymentId": "5e5ea5c16897e", + "latestDeploymentCreatedAt": "2020-10-15T06:38:00.000+00:00", + "latestDeploymentStatus": "ready", + "scopes": [], + "vars": [], + "timeout": 300.0, + "installCommand": "npm install", + "buildCommand": "npm run build", + "startCommand": "node custom-server.mjs", + "outputDirectory": "build", + "installationId": "6m40at4ejk5h2u9s1hboo", + "providerRepositoryId": "appwrite", + "providerBranch": "main", + "providerRootDirectory": "sites\/helloWorld", + "providerSilentMode": True, + "providerBranches": [], + "providerPaths": [], + "buildSpecification": "s-1vcpu-512mb", + "runtimeSpecification": "s-1vcpu-512mb", + "buildRuntime": "node-22", + "adapter": "static", + "fallbackFile": "index.html", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.update_site_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_deployments(self, m): data = { - "total": 5.0, - "deployments": [] -} + "total": 5.0, + "deployments": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.list_deployments( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create_deployment( '', InputFile.from_bytes(bytearray(), "example.file"), ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_duplicate_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create_duplicate_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_template_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create_template_deployment( '', '', @@ -400,311 +439,349 @@ def test_create_template_deployment(self, m): 'branch', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_vcs_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create_vcs_deployment( '', 'branch', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_deployment(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.get_deployment( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_deployment(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.delete_deployment( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_deployment_download(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.sites.get_deployment_download( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_deployment_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "type": "vcs", - "resourceId": "5e5ea6g16897e", - "resourceType": "functions", - "entrypoint": "index.js", - "sourceSize": 128.0, - "buildSize": 128.0, - "totalSize": 128.0, - "buildId": "5e5ea5c16897e", - "activate": True, - "screenshotLight": "5e5ea5c16897e", - "screenshotDark": "5e5ea5c16897e", - "status": "ready", - "buildLogs": "Compiling source files...", - "buildDuration": 128.0, - "providerRepositoryName": "database", - "providerRepositoryOwner": "utopia", - "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", - "providerCommitHash": "7c3f25d", - "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", - "providerCommitAuthor": "Khushboo Verma", - "providerCommitMessage": "Update index.js", - "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", - "providerBranch": "0.7.x", - "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "type": "vcs", + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "entrypoint": "index.js", + "sourceSize": 128.0, + "buildSize": 128.0, + "totalSize": 128.0, + "buildId": "5e5ea5c16897e", + "activate": True, + "screenshotLight": "5e5ea5c16897e", + "screenshotDark": "5e5ea5c16897e", + "status": "ready", + "buildLogs": "Compiling source files...", + "buildDuration": 128.0, + "providerRepositoryName": "database", + "providerRepositoryOwner": "utopia", + "providerRepositoryUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function", + "providerCommitHash": "7c3f25d", + "providerCommitAuthorUrl": "https:\/\/github.com\/vermakhushboo", + "providerCommitAuthor": "Khushboo Verma", + "providerCommitMessage": "Update index.js", + "providerCommitUrl": "https:\/\/github.com\/vermakhushboo\/g4-node-function\/commit\/60c0416257a9cbcdd96b2d370c38d8f8d150ccfb", + "providerBranch": "0.7.x", + "providerBranchUrl": "https:\/\/github.com\/vermakhushboo\/appwrite\/tree\/0.7.x", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.update_deployment_status( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_logs(self, m): data = { - "total": 5.0, - "executions": [] -} + "total": 5.0, + "executions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.list_logs( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_log(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "functionId": "5e5ea6g16897e", - "deploymentId": "5e5ea5c16897e", - "trigger": "http", - "status": "processing", - "requestMethod": "GET", - "requestPath": "\/articles?id=5", - "requestHeaders": [], - "responseStatusCode": 200.0, - "responseBody": "", - "responseHeaders": [], - "logs": "", - "errors": "", - "duration": 0.4 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "resourceId": "5e5ea6g16897e", + "resourceType": "functions", + "deploymentId": "5e5ea5c16897e", + "trigger": "http", + "status": "processing", + "requestMethod": "GET", + "requestPath": "\/articles?id=5", + "requestHeaders": [], + "responseStatusCode": 200.0, + "responseBody": "", + "responseHeaders": [], + "logs": "", + "errors": "", + "duration": 0.4, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.get_log( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_log(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.delete_log( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_variables(self, m): data = { - "total": 5.0, - "variables": [] -} + "total": 5.0, + "variables": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.list_variables( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.create_variable( '', '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.get_variable( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_variable(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "API_KEY", - "value": "myPa$$word1", - "secret": True, - "resourceType": "function", - "resourceId": "myAwesomeFunction" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "API_KEY", + "value": "myPa$$word1", + "secret": True, + "resourceType": "function", + "resourceId": "myAwesomeFunction", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.update_variable( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_variable(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.sites.delete_variable( '', '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_storage.py b/test/services/test_storage.py index af4587cb..d2e56d29 100644 --- a/test/services/test_storage.py +++ b/test/services/test_storage.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.storage import Storage + class StorageServiceTest(unittest.TestCase): def setUp(self): @@ -16,267 +17,304 @@ def setUp(self): @requests_mock.Mocker() def test_list_buckets(self, m): data = { - "total": 5.0, - "buckets": [] -} + "total": 5.0, + "buckets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.storage.list_buckets( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.storage.list_buckets() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_bucket(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "fileSecurity": True, - "name": "Documents", - "enabled": True, - "maximumFileSize": 100.0, - "allowedFileExtensions": [], - "compression": "gzip", - "encryption": True, - "antivirus": True, - "transformations": True, - "totalSize": 128.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "fileSecurity": True, + "name": "Documents", + "enabled": True, + "maximumFileSize": 100.0, + "allowedFileExtensions": [], + "compression": "gzip", + "encryption": True, + "antivirus": True, + "transformations": True, + "totalSize": 128.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.create_bucket( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_bucket(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "fileSecurity": True, - "name": "Documents", - "enabled": True, - "maximumFileSize": 100.0, - "allowedFileExtensions": [], - "compression": "gzip", - "encryption": True, - "antivirus": True, - "transformations": True, - "totalSize": 128.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "fileSecurity": True, + "name": "Documents", + "enabled": True, + "maximumFileSize": 100.0, + "allowedFileExtensions": [], + "compression": "gzip", + "encryption": True, + "antivirus": True, + "transformations": True, + "totalSize": 128.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.get_bucket( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_bucket(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "fileSecurity": True, - "name": "Documents", - "enabled": True, - "maximumFileSize": 100.0, - "allowedFileExtensions": [], - "compression": "gzip", - "encryption": True, - "antivirus": True, - "transformations": True, - "totalSize": 128.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "fileSecurity": True, + "name": "Documents", + "enabled": True, + "maximumFileSize": 100.0, + "allowedFileExtensions": [], + "compression": "gzip", + "encryption": True, + "antivirus": True, + "transformations": True, + "totalSize": 128.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.update_bucket( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_bucket(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.delete_bucket( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_files(self, m): data = { - "total": 5.0, - "files": [] -} + "total": 5.0, + "files": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.list_files( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_file(self, m): data = { - "$id": "5e5ea5c16897e", - "bucketId": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "name": "Pink.png", - "folder": "photos\/2026\/", - "key": "photos\/2026\/Pink.png", - "signature": "5d529fd02b544198ae075bd57c1762bb", - "mimeType": "image\/png", - "sizeOriginal": 17890.0, - "sizeActual": 12345.0, - "chunksTotal": 17890.0, - "chunksUploaded": 17890.0, - "encryption": True, - "compression": "gzip" -} + "$id": "5e5ea5c16897e", + "bucketId": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", + "signature": "5d529fd02b544198ae075bd57c1762bb", + "mimeType": "image\/png", + "sizeOriginal": 17890.0, + "sizeActual": 12345.0, + "chunksTotal": 17890.0, + "chunksUploaded": 17890.0, + "encryption": True, + "compression": "gzip", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.create_file( '', '', InputFile.from_bytes(bytearray(), "example.file"), ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_file(self, m): data = { - "$id": "5e5ea5c16897e", - "bucketId": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "name": "Pink.png", - "folder": "photos\/2026\/", - "key": "photos\/2026\/Pink.png", - "signature": "5d529fd02b544198ae075bd57c1762bb", - "mimeType": "image\/png", - "sizeOriginal": 17890.0, - "sizeActual": 12345.0, - "chunksTotal": 17890.0, - "chunksUploaded": 17890.0, - "encryption": True, - "compression": "gzip" -} + "$id": "5e5ea5c16897e", + "bucketId": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", + "signature": "5d529fd02b544198ae075bd57c1762bb", + "mimeType": "image\/png", + "sizeOriginal": 17890.0, + "sizeActual": 12345.0, + "chunksTotal": 17890.0, + "chunksUploaded": 17890.0, + "encryption": True, + "compression": "gzip", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.get_file( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_file(self, m): data = { - "$id": "5e5ea5c16897e", - "bucketId": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "name": "Pink.png", - "folder": "photos\/2026\/", - "key": "photos\/2026\/Pink.png", - "signature": "5d529fd02b544198ae075bd57c1762bb", - "mimeType": "image\/png", - "sizeOriginal": 17890.0, - "sizeActual": 12345.0, - "chunksTotal": 17890.0, - "chunksUploaded": 17890.0, - "encryption": True, - "compression": "gzip" -} + "$id": "5e5ea5c16897e", + "bucketId": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "name": "Pink.png", + "folder": "photos\/2026\/", + "key": "photos\/2026\/Pink.png", + "signature": "5d529fd02b544198ae075bd57c1762bb", + "mimeType": "image\/png", + "sizeOriginal": 17890.0, + "sizeActual": 12345.0, + "chunksTotal": 17890.0, + "chunksUploaded": 17890.0, + "encryption": True, + "compression": "gzip", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.update_file( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_file(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.storage.delete_file( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_file_download(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.storage.get_file_download( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_file_preview(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.storage.get_file_preview( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_file_view(self, m): data = bytearray() headers = {'Content-Type': 'application/octet-stream'} - m.request(requests_mock.ANY, requests_mock.ANY, body=data, headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + body=data, + headers=headers, + ) response = self.storage.get_file_view( '', '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_tables_db.py b/test/services/test_tables_db.py index ba339712..51f40fc4 100644 --- a/test/services/test_tables_db.py +++ b/test/services/test_tables_db.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.tables_db import TablesDB + class TablesDBServiceTest(unittest.TestCase): def setUp(self): @@ -16,1731 +17,1964 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "databases": [] -} + "total": 5.0, + "databases": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.tables_db.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.tables_db.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_specifications(self, m): data = { - "specifications": [], - "total": 9.0, - "pricing": { - "storageOverageRate": 0.125, - "bandwidthOverageRate": 0.08, - "replicaRate": 1, - "pitrRate": 0.2 - } -} + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.tables_db.list_specifications( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.tables_db.list_specifications() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_transactions(self, m): data = { - "total": 5.0, - "transactions": [] -} + "total": 5.0, + "transactions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.tables_db.list_transactions( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.tables_db.list_transactions() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.tables_db.create_transaction( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.tables_db.create_transaction() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_transaction( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_transaction(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_transaction( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_transaction(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_transaction( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_operations(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "status": "pending", - "operations": 5.0, - "expiresAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_operations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "name": "My Database", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "enabled": True, - "type": "legacy" -} + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_failover(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "projectId": "5e5ea5c16897e", - "name": "My Production Database", - "api": "postgresql", - "engine": "postgresql", - "version": "16", - "specification": "s-2vcpu-2gb", - "backend": "edge", - "hostname": "db-myproject-mydb.fra.appwrite.center", - "connectionPort": 5432.0, - "connectionUser": "appwrite_user", - "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", - "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", - "ssl": True, - "status": "ready", - "containerStatus": "active", - "lifecycleState": "active", - "idleTimeoutMinutes": 15.0, - "cpu": 2000.0, - "memory": 4096.0, - "storage": 100.0, - "storageClass": "ssd", - "storageMaxGb": 100.0, - "nodePool": "db-pool-4vcpu-8gb", - "replicas": 2.0, - "syncMode": "async", - "networkMaxConnections": 500.0, - "networkIdleTimeoutSeconds": 900.0, - "networkIPAllowlist": [], - "backupEnabled": True, - "pitr": True, - "pitrRetentionDays": 14.0, - "storageAutoscaling": True, - "storageAutoscalingThresholdPercent": 85.0, - "storageAutoscalingMaxGb": 500.0, - "maintenanceWindowDay": "sun", - "maintenanceWindowHourUtc": 3.0, - "metricsEnabled": True, - "sqlApiEnabled": True, - "sqlApiAllowedStatements": [], - "sqlApiMaxRows": 10000.0, - "sqlApiMaxBytes": 10485760.0, - "sqlApiTimeoutSeconds": 30.0, - "error": "" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_failover( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_migrations(self, m): data = { - "total": 5.0, - "migrations": [] -} + "total": 5.0, + "migrations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_migrations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_migration(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "projectId": "5e5ea5c16897e", - "databaseId": "5e5ea5c16897e", - "specification": "s-2vcpu-4gb", - "phase": "pending", - "attempt": 0.0, - "lastError": "", - "lagDocuments": 0.0, - "verifiedAt": "2020-10-15T06:38:00.000+00:00", - "cutoverAt": "2020-10-15T06:38:00.000+00:00", - "soakUntil": "2020-10-15T06:38:00.000+00:00", - "autoCutover": True, - "cutoverRequested": True, - "paused": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "changelogWatermark": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_migration( '', 's-1vcpu-1gb', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_migration(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "projectId": "5e5ea5c16897e", - "databaseId": "5e5ea5c16897e", - "specification": "s-2vcpu-4gb", - "phase": "pending", - "attempt": 0.0, - "lastError": "", - "lagDocuments": 0.0, - "verifiedAt": "2020-10-15T06:38:00.000+00:00", - "cutoverAt": "2020-10-15T06:38:00.000+00:00", - "soakUntil": "2020-10-15T06:38:00.000+00:00", - "autoCutover": True, - "cutoverRequested": True, - "paused": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "changelogWatermark": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_migration( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_migration(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_migration( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_cutover_migration(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "projectId": "5e5ea5c16897e", - "databaseId": "5e5ea5c16897e", - "specification": "s-2vcpu-4gb", - "phase": "pending", - "attempt": 0.0, - "lastError": "", - "lagDocuments": 0.0, - "verifiedAt": "2020-10-15T06:38:00.000+00:00", - "cutoverAt": "2020-10-15T06:38:00.000+00:00", - "soakUntil": "2020-10-15T06:38:00.000+00:00", - "autoCutover": True, - "cutoverRequested": True, - "paused": True -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "databaseId": "5e5ea5c16897e", + "specification": "s-2vcpu-4gb", + "phase": "pending", + "attempt": 0.0, + "lastError": "", + "lagDocuments": 0.0, + "changelogWatermark": 0.0, + "verifiedAt": "2020-10-15T06:38:00.000+00:00", + "cutoverAt": "2020-10-15T06:38:00.000+00:00", + "soakUntil": "2020-10-15T06:38:00.000+00:00", + "autoCutover": True, + "cutoverRequested": True, + "paused": True, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.cutover_migration( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_operations(self, m): data = { - "total": 5.0, - "operations": [] -} + "total": 5.0, + "operations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_operations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_replicas(self, m): data = { - "replicas": 2.0, - "syncMode": "async", - "syncDegraded": True, - "syncAcknowledgements": 1.0, - "syncStandbyCount": 2.0, - "members": [] -} + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_replicas( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_status(self, m): data = { - "health": "healthy", - "ready": True, - "engine": "postgresql", - "version": "17", - "uptime": 86400.0, - "connections": { - "current": 12.0, - "max": 100.0 - }, - "syncMode": "async", - "syncDegraded": True, - "syncAcknowledgements": 1.0, - "syncStandbyCount": 2.0, - "replicas": [], - "volumes": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_status( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_tables(self, m): data = { - "total": 5.0, - "tables": [] -} + "total": 5.0, + "tables": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_tables( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_table(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Table", - "enabled": True, - "rowSecurity": True, - "columns": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Table", + "enabled": True, + "rowSecurity": True, + "columns": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_table( '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_table(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Table", - "enabled": True, - "rowSecurity": True, - "columns": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Table", + "enabled": True, + "rowSecurity": True, + "columns": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_table( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_table(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [], - "databaseId": "5e5ea5c16897e", - "name": "My Table", - "enabled": True, - "rowSecurity": True, - "columns": [], - "indexes": [], - "bytesMax": 65535.0, - "bytesUsed": 1500.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Table", + "enabled": True, + "rowSecurity": True, + "columns": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_table( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_table(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_table( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_columns(self, m): data = { - "total": 5.0, - "columns": [] -} + "total": 5.0, + "columns": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_columns( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_big_int_column(self, m): data = { - "key": "count", - "type": "bigint", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "bigint", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_big_int_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_big_int_column(self, m): data = { - "key": "count", - "type": "bigint", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "bigint", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_big_int_column( '', '', - '', + '', True, 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_boolean_column(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_boolean_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_boolean_column(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_boolean_column( '', '', - '', + '', True, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_datetime_column(self, m): data = { - "key": "birthDay", - "type": "datetime", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "datetime" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "birthDay", + "type": "datetime", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "datetime", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_datetime_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_datetime_column(self, m): data = { - "key": "birthDay", - "type": "datetime", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "datetime" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "birthDay", + "type": "datetime", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "datetime", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_datetime_column( '', '', - '', + '', True, '2020-10-15T06:38:00.000+00:00', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_email_column(self, m): data = { - "key": "userEmail", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "email" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "userEmail", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "email", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_email_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email_column(self, m): data = { - "key": "userEmail", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "email" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "userEmail", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "email", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_email_column( '', '', - '', + '', True, 'email@example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_enum_column(self, m): data = { - "key": "status", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "elements": [], - "format": "enum" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "status", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "elements": [], + "format": "enum", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_enum_column( '', '', - '', + '', [], True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_enum_column(self, m): data = { - "key": "status", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "elements": [], - "format": "enum" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "status", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "elements": [], + "format": "enum", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_enum_column( '', '', - '', + '', [], True, - '', + 'active', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_float_column(self, m): data = { - "key": "percentageCompleted", - "type": "double", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "percentageCompleted", + "type": "double", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_float_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_float_column(self, m): data = { - "key": "percentageCompleted", - "type": "double", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "percentageCompleted", + "type": "double", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_float_column( '', '', - '', + '', True, 1.0, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_integer_column(self, m): data = { - "key": "count", - "type": "integer", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "integer", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_integer_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_integer_column(self, m): data = { - "key": "count", - "type": "integer", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "count", + "type": "integer", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_integer_column( '', '', - '', + '', True, 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_ip_column(self, m): data = { - "key": "ipAddress", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "ip" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "ipAddress", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "ip", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_ip_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_ip_column(self, m): data = { - "key": "ipAddress", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "ip" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "ipAddress", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "ip", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_ip_column( '', '', - '', + '', True, - '', + '192.0.2.0', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_line_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_line_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_line_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_line_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_longtext_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_longtext_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_longtext_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_longtext_column( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mediumtext_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_mediumtext_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mediumtext_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_mediumtext_column( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_point_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_point_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_point_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_point_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_polygon_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_polygon_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_polygon_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_polygon_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_relationship_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "relatedTable": "table", - "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", - "twoWay": True, - "twoWayKey": "string", - "onDelete": "restrict|cascade|setNull", - "side": "parent|child" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "relatedTable": "table", + "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", + "twoWay": True, + "twoWayKey": "string", + "onDelete": "restrict|cascade|setNull", + "side": "parent|child", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_relationship_column( '', '', '', 'oneToOne', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_string_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_string_column( '', '', - '', + '', 1, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_string_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_string_column( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_text_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_text_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_text_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_text_column( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_url_column(self, m): data = { - "key": "githubUrl", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "url" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "githubUrl", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "url", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_url_column( '', '', - '', + '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_url_column(self, m): data = { - "key": "githubUrl", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "format": "url" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "githubUrl", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "format": "url", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_url_column( '', '', - '', + '', True, 'https://example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_varchar_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_varchar_column( '', '', - '', + '', 1, True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_varchar_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "size": 128.0 -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "size": 128.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_varchar_column( '', '', - '', + '', True, - '', + 'Hello World', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_column(self, m): data = { - "key": "isEnabled", - "type": "boolean", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "isEnabled", + "type": "boolean", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_column( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_column(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_column( '', '', - '', + '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_relationship_column(self, m): data = { - "key": "fullName", - "type": "string", - "status": "available", - "error": "string", - "required": True, - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "relatedTable": "table", - "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", - "twoWay": True, - "twoWayKey": "string", - "onDelete": "restrict|cascade|setNull", - "side": "parent|child" -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "key": "fullName", + "type": "string", + "status": "available", + "error": "string", + "required": True, + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "relatedTable": "table", + "relationType": "oneToOne|oneToMany|manyToOne|manyToMany", + "twoWay": True, + "twoWayKey": "string", + "onDelete": "restrict|cascade|setNull", + "side": "parent|child", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_relationship_column( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_indexes(self, m): data = { - "total": 5.0, - "indexes": [] -} + "total": 5.0, + "indexes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_indexes( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_index(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "index1", - "type": "primary", - "status": "available", - "error": "string", - "columns": [], - "lengths": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "columns": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_index( '', '', - '', + '', 'key', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_index(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "key": "index1", - "type": "primary", - "status": "available", - "error": "string", - "columns": [], - "lengths": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "columns": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_index( '', '', - '', + '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_index(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_index( '', '', - '', + '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_rows(self, m): data = { - "total": 5.0, - "rows": [] -} + "total": 5.0, + "rows": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.list_rows( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_row(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_row( '', '', '', {}, ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_rows(self, m): data = { - "total": 5.0, - "rows": [] -} + "total": 5.0, + "rows": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.create_rows( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_upsert_rows(self, m): data = { - "total": 5.0, - "rows": [] -} + "total": 5.0, + "rows": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.upsert_rows( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_rows(self, m): data = { - "total": 5.0, - "rows": [] -} + "total": 5.0, + "rows": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_rows( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_rows(self, m): data = { - "total": 5.0, - "rows": [] -} + "total": 5.0, + "rows": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_rows( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_row(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.get_row( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_upsert_row(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.upsert_row( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_row(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.update_row( '', '', '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @@ -1748,61 +1982,69 @@ def test_update_row(self, m): def test_delete_row(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.delete_row( '', '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_decrement_row_column(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.decrement_row_column( '', '', '', - '', + '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_increment_row_column(self, m): data = { - "$id": "5e5ea5c16897e", - "$sequence": "1", - "$tableId": "5e5ea5c15117e", - "$databaseId": "5e5ea5c15117e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "$permissions": [] -} - headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$tableId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tables_db.increment_row_column( '', '', '', - '', + '', ) - data['data'] = {} self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_teams.py b/test/services/test_teams.py index 9c2635f5..24f7dbb5 100644 --- a/test/services/test_teams.py +++ b/test/services/test_teams.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.teams import Teams + class TeamsServiceTest(unittest.TestCase): def setUp(self): @@ -16,354 +17,406 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "teams": [] -} + "total": 5.0, + "teams": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.teams.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.teams.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "VIP", - "total": 7.0, - "prefs": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.create( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "VIP", - "total": 7.0, - "prefs": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_name(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "VIP", - "total": 7.0, - "prefs": {} -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "VIP", + "total": 7.0, + "prefs": {}, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.update_name( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_installations(self, m): data = { - "total": 5.0, - "installations": [] -} + "total": 5.0, + "installations": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.list_installations( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.create_installation( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.get_installation( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_installation(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "appId": "5e5ea5c16897e", - "teamId": "5e5ea5c16897e", - "scopes": [], - "authorizationDetails": {}, - "createdById": "5e5ea5c16897e", - "createdByName": "Walter White" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "appId": "5e5ea5c16897e", + "teamId": "5e5ea5c16897e", + "scopes": [], + "authorizationDetails": [], + "createdById": "5e5ea5c16897e", + "createdByName": "Walter White", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.update_installation( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_installation(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.delete_installation( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_list_memberships(self, m): data = { - "total": 5.0, - "memberships": [] -} + "total": 5.0, + "memberships": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.list_memberships( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.create_membership( '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.get_membership( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_membership(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.update_membership( '', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_membership(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.delete_membership( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_membership_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c16897e", - "userName": "John Doe", - "userEmail": "john@appwrite.io", - "userPhone": "+1 555 555 5555", - "teamId": "5e5ea5c16897e", - "teamName": "VIP", - "invited": "2020-10-15T06:38:00.000+00:00", - "joined": "2020-10-15T06:38:00.000+00:00", - "confirm": True, - "mfa": True, - "userAccessedAt": "2020-10-15T06:38:00.000+00:00", - "roles": [] -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c16897e", + "userName": "John Doe", + "userEmail": "john@appwrite.io", + "userPhone": "+1 555 555 5555", + "teamId": "5e5ea5c16897e", + "teamName": "VIP", + "invited": "2020-10-15T06:38:00.000+00:00", + "joined": "2020-10-15T06:38:00.000+00:00", + "confirm": True, + "mfa": True, + "userAccessedAt": "2020-10-15T06:38:00.000+00:00", + "roles": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.update_membership_status( '', '', '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_prefs(self, m): data = {} headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.get_prefs( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_prefs(self, m): data = {} headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.teams.update_prefs( '', {}, ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_tokens.py b/test/services/test_tokens.py index 98073aa9..de5f3f87 100644 --- a/test/services/test_tokens.py +++ b/test/services/test_tokens.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.tokens import Tokens + class TokensServiceTest(unittest.TestCase): def setUp(self): @@ -16,89 +17,103 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "tokens": [] -} + "total": 5.0, + "tokens": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tokens.list( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_file_token(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", - "resourceType": "files", - "expire": "2020-10-15T06:38:00.000+00:00", - "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", + "resourceType": "files", + "expire": "2020-10-15T06:38:00.000+00:00", + "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tokens.create_file_token( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", - "resourceType": "files", - "expire": "2020-10-15T06:38:00.000+00:00", - "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", + "resourceType": "files", + "expire": "2020-10-15T06:38:00.000+00:00", + "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tokens.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", - "resourceType": "files", - "expire": "2020-10-15T06:38:00.000+00:00", - "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "resourceId": "5e5ea5c168bb8:5e5ea5c168bb8", + "resourceType": "files", + "expire": "2020-10-15T06:38:00.000+00:00", + "secret": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tokens.update( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.tokens.delete( '', ) - self.assertEqual(response, data) - diff --git a/test/services/test_users.py b/test/services/test_users.py index efb2130d..22288922 100644 --- a/test/services/test_users.py +++ b/test/services/test_users.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.users import Users + class UsersServiceTest(unittest.TestCase): def setUp(self): @@ -16,219 +17,245 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "users": [] -} + "total": 5.0, + "users": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.users.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.users.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_argon2_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_argon2_user( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_bcrypt_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_bcrypt_user( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_identities(self, m): data = { - "total": 5.0, - "identities": [] -} + "total": 5.0, + "identities": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.users.list_identities( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.users.list_identities() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_identity(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_identity( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_md5_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_md5_user( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_ph_pass_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_ph_pass_user( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_scrypt_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_scrypt_user( '', 'email@example.com', @@ -239,32 +266,35 @@ def test_create_scrypt_user(self, m): 1, 1, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_scrypt_modified_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_scrypt_modified_user( '', 'email@example.com', @@ -273,839 +303,957 @@ def test_create_scrypt_modified_user(self, m): '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_sha_user(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_sha_user( '', 'email@example.com', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_email(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_email( '', 'email@example.com', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_impersonator(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_impersonator( '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_jwt(self, m): data = { - "jwt": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c" -} + "jwt": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_jwt( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_labels(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_labels( '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_logs(self, m): data = { - "total": 5.0, - "logs": [] -} + "total": 5.0, + "logs": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_logs( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_memberships(self, m): data = { - "total": 5.0, - "memberships": [] -} + "total": 5.0, + "memberships": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_memberships( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_mfa( '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_mfa( '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_mfa_authenticator(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_mfa_authenticator( '', 'totp', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_delete_mfa_authenticator(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_mfa_authenticator( '', 'totp', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_get_mfa_challenge(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "expire": "2020-10-15T06:38:00.000+00:00", - "code": "446372" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "expire": "2020-10-15T06:38:00.000+00:00", + "code": "446372", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get_mfa_challenge( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_mfa_factors(self, m): data = { - "totp": True, - "phone": True, - "email": True, - "recoveryCode": True, - "custom": True -} + "totp": True, + "phone": True, + "email": True, + "recoveryCode": True, + "custom": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_mfa_factors( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_mfa_factors(self, m): data = { - "totp": True, - "phone": True, - "email": True, - "recoveryCode": True, - "custom": True -} + "totp": True, + "phone": True, + "email": True, + "recoveryCode": True, + "custom": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_mfa_factors( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_mfa_recovery_codes(self, m): data = { - "recoveryCodes": [] -} + "recoveryCodes": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_mfa_recovery_codes( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_name(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_name( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_password(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_password( '', 'password', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_phone(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_phone( '', '+12065550100', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_prefs(self, m): data = {} headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get_prefs( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_prefs(self, m): data = {} headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_prefs( '', {}, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_sessions(self, m): data = { - "total": 5.0, - "sessions": [] -} + "total": 5.0, + "sessions": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_sessions( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_session(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5bb8c16897e", - "expire": "2020-10-15T06:38:00.000+00:00", - "provider": "email", - "providerUid": "user@example.com", - "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", - "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", - "ip": "127.0.0.1", - "osCode": "Mac", - "osName": "Mac", - "osVersion": "Mac", - "clientType": "browser", - "clientCode": "CM", - "clientName": "Chrome Mobile iOS", - "clientVersion": "84.0", - "clientEngine": "WebKit", - "clientEngineVersion": "605.1.15", - "deviceName": "smartphone", - "deviceBrand": "Google", - "deviceModel": "Nexus 5", - "countryCode": "US", - "countryName": "United States", - "current": True, - "factors": [], - "secret": "5e5bb8c16897e", - "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5bb8c16897e", + "expire": "2020-10-15T06:38:00.000+00:00", + "provider": "email", + "providerUid": "user@example.com", + "providerAccessToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "providerAccessTokenExpiry": "2020-10-15T06:38:00.000+00:00", + "providerRefreshToken": "MTQ0NjJkZmQ5OTM2NDE1ZTZjNGZmZjI3", + "ip": "127.0.0.1", + "osCode": "Mac", + "osName": "Mac", + "osVersion": "Mac", + "clientType": "browser", + "clientCode": "CM", + "clientName": "Chrome Mobile iOS", + "clientVersion": "84.0", + "clientEngine": "WebKit", + "clientEngineVersion": "605.1.15", + "deviceName": "smartphone", + "deviceBrand": "Google", + "deviceModel": "Nexus 5", + "countryCode": "US", + "countryName": "United States", + "current": True, + "factors": [], + "secret": "5e5bb8c16897e", + "mfaUpdatedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_session( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_sessions(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_sessions( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_delete_session(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_session( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_status(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_status( '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_list_targets(self, m): data = { - "total": 5.0, - "targets": [] -} + "total": 5.0, + "targets": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.list_targets( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create_target(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Apple iPhone 12", - "userId": "259125845563242502", - "providerType": "email", - "identifier": "token", - "expired": True -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Apple iPhone 12", + "userId": "259125845563242502", + "providerType": "email", + "identifier": "token", + "expired": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_target( '', '', 'email', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get_target(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Apple iPhone 12", - "userId": "259125845563242502", - "providerType": "email", - "identifier": "token", - "expired": True -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Apple iPhone 12", + "userId": "259125845563242502", + "providerType": "email", + "identifier": "token", + "expired": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.get_target( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_target(self, m): data = { - "$id": "259125845563242502", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "Apple iPhone 12", - "userId": "259125845563242502", - "providerType": "email", - "identifier": "token", - "expired": True -} + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "Apple iPhone 12", + "userId": "259125845563242502", + "providerType": "email", + "identifier": "token", + "expired": True, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_target( '', '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete_target(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.delete_target( '', '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_create_token(self, m): data = { - "$id": "bb8ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "userId": "5e5ea5c168bb8", - "secret": "", - "expire": "2020-10-15T06:38:00.000+00:00", - "phrase": "Golden Fox" -} + "$id": "bb8ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "userId": "5e5ea5c168bb8", + "secret": "", + "expire": "2020-10-15T06:38:00.000+00:00", + "phrase": "Golden Fox", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.create_token( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_email_verification(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_email_verification( '', True, ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update_phone_verification(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "John Doe", - "registration": "2020-10-15T06:38:00.000+00:00", - "status": True, - "labels": [], - "passwordUpdate": "2020-10-15T06:38:00.000+00:00", - "email": "john@appwrite.io", - "phone": "+4930901820", - "emailVerification": True, - "phoneVerification": True, - "mfa": True, - "prefs": {}, - "targets": [], - "accessedAt": "2020-10-15T06:38:00.000+00:00" -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "John Doe", + "registration": "2020-10-15T06:38:00.000+00:00", + "status": True, + "labels": [], + "passwordUpdate": "2020-10-15T06:38:00.000+00:00", + "email": "john@appwrite.io", + "phone": "+4930901820", + "emailVerification": True, + "phoneVerification": True, + "mfa": True, + "prefs": {}, + "targets": [], + "accessedAt": "2020-10-15T06:38:00.000+00:00", + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.users.update_phone_verification( '', True, ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/services/test_vectors_db.py b/test/services/test_vectors_db.py new file mode 100644 index 00000000..4529586d --- /dev/null +++ b/test/services/test_vectors_db.py @@ -0,0 +1,843 @@ +import json +import requests_mock +import unittest + +from appwrite.client import Client +from appwrite.input_file import InputFile +from appwrite.models import * +from appwrite.services.vectors_db import VectorsDB + + +class VectorsDBServiceTest(unittest.TestCase): + + def setUp(self): + self.client = Client() + self.vectors_db = VectorsDB(self.client) + + @requests_mock.Mocker() + def test_list(self, m): + data = { + "total": 5.0, + "databases": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_specifications(self, m): + data = { + "specifications": [], + "total": 9.0, + "pricing": { + "storageOverageRate": 0.125, + "bandwidthOverageRate": 0.08, + "replicaRate": 1, + "pitrRate": 0.2, + }, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_specifications() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_transactions(self, m): + data = { + "total": 5.0, + "transactions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_transactions() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_transaction() + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_transaction( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_transaction(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.update_transaction( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_transaction(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete_transaction( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_create_operations(self, m): + data = { + "$id": "259125845563242502", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "status": "pending", + "operations": 5.0, + "expiresAt": "2020-10-15T06:38:00.000+00:00", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update(self, m): + data = { + "$id": "5e5ea5c16897e", + "name": "My Database", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "enabled": True, + "type": "legacy", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.update( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete( + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_collections(self, m): + data = { + "total": 5.0, + "collections": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_collections( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + "dimension": 1536.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_collection( + '', + '', + '', + 1, + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + "dimension": 1536.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_collection( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_collection(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + "databaseId": "5e5ea5c16897e", + "name": "My Collection", + "enabled": True, + "documentSecurity": True, + "attributes": [], + "indexes": [], + "bytesMax": 65535.0, + "bytesUsed": 1500.0, + "dimension": 1536.0, + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.update_collection( + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_collection(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete_collection( + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_document( + '', + '', + '', + {}, + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_documents( + '', + '', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_upsert_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.upsert_documents( + '', + '', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.update_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_documents(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete_documents( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_query(self, m): + data = { + "total": 5.0, + "documents": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_query( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_upsert_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.upsert_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_update_document(self, m): + data = { + "$id": "5e5ea5c16897e", + "$sequence": "1", + "$collectionId": "5e5ea5c15117e", + "$databaseId": "5e5ea5c15117e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "$permissions": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.update_document( + '', + '', + '', + ) + data['data'] = {} + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_document(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete_document( + '', + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_list_indexes(self, m): + data = { + "total": 5.0, + "indexes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_indexes( + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_create_index(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_index( + '', + '', + '', + 'hnsw_euclidean', + [], + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_index(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "key": "index1", + "type": "primary", + "status": "available", + "error": "string", + "attributes": [], + "lengths": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_index( + '', + '', + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_delete_index(self, m): + data = '' + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.delete_index( + '', + '', + '', + ) + self.assertEqual(response, data) + + @requests_mock.Mocker() + def test_create_failover(self, m): + data = { + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "projectId": "5e5ea5c16897e", + "name": "My Production Database", + "api": "postgresql", + "engine": "postgresql", + "version": "16", + "specification": "s-2vcpu-2gb", + "backend": "edge", + "hostname": "db-myproject-mydb.fra.appwrite.center", + "connectionPort": 5432.0, + "connectionUser": "appwrite_user", + "connectionPassword": "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", + "connectionString": "postgresql:\/\/user:pass@db-myproject-mydb.fra.appwrite.center:5432\/postgres?sslmode=require", + "ssl": True, + "status": "ready", + "containerStatus": "active", + "lifecycleState": "active", + "idleTimeoutMinutes": 15.0, + "cpu": 2000.0, + "memory": 4096.0, + "storage": 100.0, + "storageClass": "ssd", + "storageMaxGb": 100.0, + "nodePool": "db-pool-4vcpu-8gb", + "replicas": 2.0, + "syncMode": "async", + "networkMaxConnections": 500.0, + "networkIdleTimeoutSeconds": 900.0, + "networkIPAllowlist": [], + "backupEnabled": True, + "pitr": True, + "pitrRetentionDays": 14.0, + "storageAutoscaling": True, + "storageAutoscalingThresholdPercent": 85.0, + "storageAutoscalingMaxGb": 500.0, + "maintenanceWindowDay": "sun", + "maintenanceWindowHourUtc": 3.0, + "metricsEnabled": True, + "sqlApiEnabled": True, + "sqlApiAllowedStatements": [], + "sqlApiMaxRows": 10000.0, + "sqlApiMaxBytes": 10485760.0, + "sqlApiTimeoutSeconds": 30.0, + "error": "", + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.create_failover( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_list_operations(self, m): + data = { + "total": 5.0, + "operations": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.list_operations( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_replicas(self, m): + data = { + "replicas": 2.0, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "members": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_replicas( + '', + ) + self.assertEqual(response.to_dict(), data) + + @requests_mock.Mocker() + def test_get_status(self, m): + data = { + "health": "healthy", + "ready": True, + "engine": "postgresql", + "version": "17", + "uptime": 86400.0, + "connections": { + "current": 12.0, + "max": 100.0, + }, + "syncMode": "async", + "syncDegraded": True, + "syncAcknowledgements": 1.0, + "syncStandbyCount": 2.0, + "replicas": [], + "volumes": [], + } + headers = {'Content-Type': 'application/json'} + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) + response = self.vectors_db.get_status( + '', + ) + self.assertEqual(response.to_dict(), data) diff --git a/test/services/test_webhooks.py b/test/services/test_webhooks.py index c5e4e219..9d5d6237 100644 --- a/test/services/test_webhooks.py +++ b/test/services/test_webhooks.py @@ -7,6 +7,7 @@ from appwrite.models import * from appwrite.services.webhooks import Webhooks + class WebhooksServiceTest(unittest.TestCase): def setUp(self): @@ -16,136 +17,152 @@ def setUp(self): @requests_mock.Mocker() def test_list(self, m): data = { - "total": 5.0, - "webhooks": [] -} + "total": 5.0, + "webhooks": [], + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - - response = self.webhooks.list( + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, ) - + response = self.webhooks.list() self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_create(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Webhook", - "url": "https:\/\/example.com\/webhook", - "events": [], - "tls": True, - "authUsername": "username", - "authPassword": "webhook-password", - "secret": "ad3d581ca230e2b7059c545e5a", - "enabled": True, - "logs": "Failed to connect to remote server.", - "attempts": 10.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Webhook", + "url": "https:\/\/example.com\/webhook", + "events": [], + "tls": True, + "authUsername": "username", + "authPassword": "webhook-password", + "secret": "ad3d581ca230e2b7059c545e5a", + "enabled": True, + "logs": "Failed to connect to remote server.", + "attempts": 10.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.webhooks.create( '', - '', + 'https://example.com/webhook', '', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_get(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Webhook", - "url": "https:\/\/example.com\/webhook", - "events": [], - "tls": True, - "authUsername": "username", - "authPassword": "webhook-password", - "secret": "ad3d581ca230e2b7059c545e5a", - "enabled": True, - "logs": "Failed to connect to remote server.", - "attempts": 10.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Webhook", + "url": "https:\/\/example.com\/webhook", + "events": [], + "tls": True, + "authUsername": "username", + "authPassword": "webhook-password", + "secret": "ad3d581ca230e2b7059c545e5a", + "enabled": True, + "logs": "Failed to connect to remote server.", + "attempts": 10.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.webhooks.get( '', ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_update(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Webhook", - "url": "https:\/\/example.com\/webhook", - "events": [], - "tls": True, - "authUsername": "username", - "authPassword": "webhook-password", - "secret": "ad3d581ca230e2b7059c545e5a", - "enabled": True, - "logs": "Failed to connect to remote server.", - "attempts": 10.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Webhook", + "url": "https:\/\/example.com\/webhook", + "events": [], + "tls": True, + "authUsername": "username", + "authPassword": "webhook-password", + "secret": "ad3d581ca230e2b7059c545e5a", + "enabled": True, + "logs": "Failed to connect to remote server.", + "attempts": 10.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.webhooks.update( '', '', - '', + 'https://example.com/webhook', [], ) - self.assertEqual(response.to_dict(), data) @requests_mock.Mocker() def test_delete(self, m): data = '' headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.webhooks.delete( '', ) - self.assertEqual(response, data) @requests_mock.Mocker() def test_update_secret(self, m): data = { - "$id": "5e5ea5c16897e", - "$createdAt": "2020-10-15T06:38:00.000+00:00", - "$updatedAt": "2020-10-15T06:38:00.000+00:00", - "name": "My Webhook", - "url": "https:\/\/example.com\/webhook", - "events": [], - "tls": True, - "authUsername": "username", - "authPassword": "webhook-password", - "secret": "ad3d581ca230e2b7059c545e5a", - "enabled": True, - "logs": "Failed to connect to remote server.", - "attempts": 10.0 -} + "$id": "5e5ea5c16897e", + "$createdAt": "2020-10-15T06:38:00.000+00:00", + "$updatedAt": "2020-10-15T06:38:00.000+00:00", + "name": "My Webhook", + "url": "https:\/\/example.com\/webhook", + "events": [], + "tls": True, + "authUsername": "username", + "authPassword": "webhook-password", + "secret": "ad3d581ca230e2b7059c545e5a", + "enabled": True, + "logs": "Failed to connect to remote server.", + "attempts": 10.0, + } headers = {'Content-Type': 'application/json'} - m.request(requests_mock.ANY, requests_mock.ANY, text=json.dumps(data), headers=headers) - + m.request( + requests_mock.ANY, + requests_mock.ANY, + text=json.dumps(data), + headers=headers, + ) response = self.webhooks.update_secret( '', ) - self.assertEqual(response.to_dict(), data) - diff --git a/test/test_id.py b/test/test_id.py index 280433d4..6c7eb2a4 100644 --- a/test/test_id.py +++ b/test/test_id.py @@ -2,6 +2,7 @@ from appwrite.id import ID + class TestIDMethods(unittest.TestCase): def test_unique(self): diff --git a/test/test_operator.py b/test/test_operator.py index f85ec6ec..881f3282 100644 --- a/test/test_operator.py +++ b/test/test_operator.py @@ -2,6 +2,7 @@ from appwrite.operator import Operator, Condition + class TestOperatorMethods(unittest.TestCase): def test_increment(self): @@ -38,10 +39,14 @@ def test_power_with_max(self): self.assertEqual(Operator.power(3, 100), '{"method":"power","values":[3,100]}') def test_array_append(self): - self.assertEqual(Operator.array_append(['item1', 'item2']), '{"method":"arrayAppend","values":["item1","item2"]}') + self.assertEqual( + Operator.array_append(['item1', 'item2']), '{"method":"arrayAppend","values":["item1","item2"]}' + ) def test_array_prepend(self): - self.assertEqual(Operator.array_prepend(['first', 'second']), '{"method":"arrayPrepend","values":["first","second"]}') + self.assertEqual( + Operator.array_prepend(['first', 'second']), '{"method":"arrayPrepend","values":["first","second"]}' + ) def test_array_insert(self): self.assertEqual(Operator.array_insert(0, 'newItem'), '{"method":"arrayInsert","values":[0,"newItem"]}') @@ -53,13 +58,17 @@ def test_array_unique(self): self.assertEqual(Operator.array_unique(), '{"method":"arrayUnique","values":[]}') def test_array_intersect(self): - self.assertEqual(Operator.array_intersect(['a', 'b', 'c']), '{"method":"arrayIntersect","values":["a","b","c"]}') + self.assertEqual( + Operator.array_intersect(['a', 'b', 'c']), '{"method":"arrayIntersect","values":["a","b","c"]}' + ) def test_array_diff(self): self.assertEqual(Operator.array_diff(['x', 'y']), '{"method":"arrayDiff","values":["x","y"]}') def test_array_filter(self): - self.assertEqual(Operator.array_filter(Condition.EQUAL, 'test'), '{"method":"arrayFilter","values":["equal","test"]}') + self.assertEqual( + Operator.array_filter(Condition.EQUAL, 'test'), '{"method":"arrayFilter","values":["equal","test"]}' + ) def test_string_concat(self): self.assertEqual(Operator.string_concat('suffix'), '{"method":"stringConcat","values":["suffix"]}') diff --git a/test/test_permission.py b/test/test_permission.py index 54e66429..50463126 100644 --- a/test/test_permission.py +++ b/test/test_permission.py @@ -3,6 +3,7 @@ from appwrite.permission import Permission from appwrite.role import Role + class TestPermissionMethods(unittest.TestCase): def test_read(self): diff --git a/test/test_query.py b/test/test_query.py index c8595b5c..055fd575 100644 --- a/test/test_query.py +++ b/test/test_query.py @@ -2,12 +2,14 @@ from appwrite.query import Query + class BasicFilterQueryTest: def __init__(self, description: str, value, expected_values: str): self.description = description self.value = value self.expected_values = expected_values + tests = [ BasicFilterQueryTest('with a string', 's', '["s"]'), BasicFilterQueryTest('with an integer', 1, '[1]'), @@ -17,6 +19,7 @@ def __init__(self, description: str, value, expected_values: str): BasicFilterQueryTest('with a list', ['a', 'b', 'c'], '["a","b","c"]'), ] + class TestQueryMethods(unittest.TestCase): def test_equal(self): @@ -24,7 +27,7 @@ def test_equal(self): self.assertEqual( Query.equal('attr', t.value), f'{{"method":"equal","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_not_equal(self): @@ -32,7 +35,7 @@ def test_not_equal(self): self.assertEqual( Query.not_equal('attr', t.value), f'{{"method":"notEqual","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_less_than(self): @@ -40,7 +43,7 @@ def test_less_than(self): self.assertEqual( Query.less_than('attr', t.value), f'{{"method":"lessThan","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_less_than_equal(self): @@ -48,7 +51,7 @@ def test_less_than_equal(self): self.assertEqual( Query.less_than_equal('attr', t.value), f'{{"method":"lessThanEqual","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_greater_than(self): @@ -56,7 +59,7 @@ def test_greater_than(self): self.assertEqual( Query.greater_than('attr', t.value), f'{{"method":"greaterThan","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_greater_than_equal(self): @@ -64,11 +67,14 @@ def test_greater_than_equal(self): self.assertEqual( Query.greater_than_equal('attr', t.value), f'{{"method":"greaterThanEqual","attribute":"attr","values":{t.expected_values}}}', - t.description + t.description, ) def test_search(self): - self.assertEqual(Query.search('attr', 'keyword1 keyword2'), '{"method":"search","attribute":"attr","values":["keyword1 keyword2"]}') + self.assertEqual( + Query.search('attr', 'keyword1 keyword2'), + '{"method":"search","attribute":"attr","values":["keyword1 keyword2"]}', + ) def test_is_null(self): self.assertEqual(Query.is_null('attr'), '{"method":"isNull","attribute":"attr"}') diff --git a/test/test_role.py b/test/test_role.py index 53311275..8ce4763e 100644 --- a/test/test_role.py +++ b/test/test_role.py @@ -2,6 +2,7 @@ from appwrite.role import Role + class TestRoleMethods(unittest.TestCase): def test_any(self): From 05cbbcdf74c884afc00f689254e5c97761297659 Mon Sep 17 00:00:00 2001 From: Chirag Aggarwal Date: Thu, 27 Aug 2026 18:28:03 +0530 Subject: [PATCH 10/10] chore: update Python SDK to 24.0.0rc1 --- CHANGELOG.md | 6 +++++- appwrite/client.py | 4 ++-- pyproject.toml | 2 +- setup.py | 4 ++-- 4 files changed, 10 insertions(+), 6 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index de574a2f..cc22931a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,11 @@ # Change Log -## 23.1.0rc1 +## 24.0.0rc1 +* Breaking: `Execution.functionId` is replaced by `resourceId` and `resourceType`, now that executions cover both functions and sites +* Breaking: `AppInstallation.authorizationDetails` is now an array instead of an object +* Breaking: removed `dedicatedDatabases.execute` from `ProjectKeyScopes` +* Breaking: `EmbeddingModel` no longer offers `embedding-gemma` or `bge-small` * Added: `documentsDB`, `vectorsDB`, `mysql`, `postgresql`, and `mongo` services, no longer hidden from server SDKs * Added: `DocumentsDBIndexType` and `VectorsDBIndexType` enums * Added: dedicated database models for branches, backups, restorations, poolers, PITR windows, extensions, and executions diff --git a/appwrite/client.py b/appwrite/client.py index b79625dc..c102cc0e 100644 --- a/appwrite/client.py +++ b/appwrite/client.py @@ -18,11 +18,11 @@ def __init__(self): self._endpoint = 'https://cloud.appwrite.io/v1' self._global_headers = { 'content-type': '', - 'user-agent': f'AppwritePythonSDK/23.1.0rc1 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', + 'user-agent': f'AppwritePythonSDK/24.0.0rc1 ({platform.uname().system}; {platform.uname().version}; {platform.uname().machine})', 'x-sdk-name': 'Python', 'x-sdk-platform': 'server', 'x-sdk-language': 'python', - 'x-sdk-version': '23.1.0rc1', + 'x-sdk-version': '24.0.0rc1', 'X-Appwrite-Response-Format': '1.9.6', } self._config = {} diff --git a/pyproject.toml b/pyproject.toml index 137cee0d..17cd6a75 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta" [project] name = "appwrite" -version = "23.1.0rc1" +version = "24.0.0rc1" description = "Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API" readme = "README.md" requires-python = ">=3.9" diff --git a/setup.py b/setup.py index c8a24937..1d8e7ce3 100644 --- a/setup.py +++ b/setup.py @@ -8,7 +8,7 @@ setuptools.setup( name='appwrite', packages=setuptools.find_packages(), - version='23.1.0rc1', + version='24.0.0rc1', license='BSD-3-Clause', description='Appwrite is an open-source self-hosted backend server that abstracts and simplifies complex and repetitive development tasks behind a very simple REST API', long_description=long_description, @@ -18,7 +18,7 @@ maintainer='Appwrite Team', maintainer_email='team@appwrite.io', url='https://appwrite.io/support', - download_url='https://github.com/appwrite/sdk-for-python/archive/23.1.0rc1.tar.gz', + download_url='https://github.com/appwrite/sdk-for-python/archive/24.0.0rc1.tar.gz', install_requires=[ 'requests', 'pydantic>=2,<3',