From 67c8de2e481a7363c2be23e7efc5a7db6bab43c2 Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Thu, 29 Feb 2024 02:13:19 -0500 Subject: [PATCH 01/11] add dj-rest-auth --- config/api_router.py | 9 ++++++++- config/settings/base.py | 1 + config/settings/local.py | 2 +- config/urls.py | 3 +-- democrasite/users/api/views.py | 13 +++++++++++++ democrasite/webiscite/models.py | 18 +++++++++--------- democrasite/webiscite/views.py | 2 +- requirements/base.txt | 1 + 8 files changed, 35 insertions(+), 14 deletions(-) diff --git a/config/api_router.py b/config/api_router.py index a53e70c..aab8334 100644 --- a/config/api_router.py +++ b/config/api_router.py @@ -1,7 +1,10 @@ from django.conf import settings +from django.urls import include +from django.urls import path from rest_framework.routers import DefaultRouter from rest_framework.routers import SimpleRouter +from democrasite.users.api.views import GitHubLogin from democrasite.users.api.views import UserViewSet from democrasite.webiscite.api.views import BillViewSet @@ -13,4 +16,8 @@ # Unfortunately if we want automatical links for models we can't use a namespace # but I may reconsider anyway # app_name = "api" # noqa: ERA001 -urlpatterns = router.urls +urlpatterns = [ + *router.urls, + path("auth/", include("dj_rest_auth.urls")), + path("auth/github/", GitHubLogin.as_view(), name="github_login"), +] diff --git a/config/settings/base.py b/config/settings/base.py index a9109a5..c5f15a1 100644 --- a/config/settings/base.py +++ b/config/settings/base.py @@ -95,6 +95,7 @@ "rest_framework.authtoken", "corsheaders", "drf_spectacular", + "dj_rest_auth", # Machina (forum) dependencies: "mptt", "haystack", diff --git a/config/settings/local.py b/config/settings/local.py index 0b79845..14c7aec 100644 --- a/config/settings/local.py +++ b/config/settings/local.py @@ -19,7 +19,7 @@ # https://docs.djangoproject.com/en/dev/ref/settings/#allowed-hosts ALLOWED_HOSTS = ["localhost", "0.0.0.0", "127.0.0.1"] # noqa: S104 # Admin site is only enabled during development -INSTALLED_APPS += ["django.contrib.admin"] # type: ignore[used-before-def] +INSTALLED_APPS += ["django.contrib.admin"] # CACHES # ------------------------------------------------------------------------------ diff --git a/config/urls.py b/config/urls.py index 049c2e4..1e0f22c 100644 --- a/config/urls.py +++ b/config/urls.py @@ -10,7 +10,6 @@ from django.views.generic import TemplateView from drf_spectacular.views import SpectacularAPIView from drf_spectacular.views import SpectacularSwaggerView -from rest_framework.authtoken.views import obtain_auth_token urlpatterns = [ path( @@ -37,7 +36,7 @@ # API base url path("api/", include("config.api_router")), # DRF auth token - path("auth-token/", obtain_auth_token), + path("api/auth", include("dj_rest_auth.urls")), path("api/schema/", SpectacularAPIView.as_view(), name="api-schema"), path( "api/docs/", diff --git a/democrasite/users/api/views.py b/democrasite/users/api/views.py index d28633c..72790de 100644 --- a/democrasite/users/api/views.py +++ b/democrasite/users/api/views.py @@ -1,3 +1,7 @@ +from allauth.socialaccount.providers.github.views import GitHubOAuth2Adapter +from allauth.socialaccount.providers.oauth2.client import OAuth2Client +from dj_rest_auth.registration.views import SocialLoginView +from django.urls import reverse from rest_framework import status from rest_framework.decorators import action from rest_framework.mixins import ListModelMixin @@ -24,3 +28,12 @@ def get_queryset(self, *args, **kwargs): def me(self, request): serializer = UserSerializer(request.user, context={"request": request}) return Response(status=status.HTTP_200_OK, data=serializer.data) + + +# dj-rest-auth views + + +class GitHubLogin(SocialLoginView): + adapter_class = GitHubOAuth2Adapter + callback_url = reverse("github_callback") + client_class = OAuth2Client diff --git a/democrasite/webiscite/models.py b/democrasite/webiscite/models.py index 4b07fc6..cb9f964 100644 --- a/democrasite/webiscite/models.py +++ b/democrasite/webiscite/models.py @@ -3,6 +3,8 @@ import json from logging import getLogger from typing import Any +from typing import Self +from typing import cast import requests from django.conf import settings @@ -57,7 +59,7 @@ def __str__(self) -> str: return f"PR #{self.number}" @classmethod - def create_from_pr(cls, pr: dict[str, Any]) -> "PullRequest": + def create_from_pr(cls, pr: dict[str, Any]) -> Self: """Update or create a pull request from a parsed JSON object representing the it If the given pull request exists, update it based on the request, otherwise @@ -84,7 +86,8 @@ def create_from_pr(cls, pr: dict[str, Any]) -> "PullRequest": act = "created" if created else "updated" logger.info("PR %s: Pull request %s", pr["number"], act) - return pull_request + + return cast(Self, pull_request) # mypy infers wrong type (Pylance doesn't 👀) def close(self) -> "Bill | None": """Close a pull request and update the local representation @@ -148,9 +151,6 @@ class Status(models.TextChoices): PeriodicTask, on_delete=models.PROTECT, null=True, blank=True ) - # TODO: Add a custom manager with a queryset method to get open bills - # (get manager from queryset) - class Meta: constraints = [ models.UniqueConstraint( @@ -179,7 +179,7 @@ def yes_votes(self) -> models.QuerySet[User]: def no_votes(self) -> models.QuerySet[User]: return self.votes.filter(vote__support=False) - def vote(self, user: User, *, support: bool): + def vote(self, user: User, *, support: bool) -> None: """Sets the given user's vote based on the support parameter If the user already voted the way the method would set, their vote is @@ -199,10 +199,10 @@ def vote(self, user: User, *, support: bool): except Vote.DoesNotExist: # Stubs issue fixed (by me!) in https://github.com/typeddjango/django-stubs/pull/1943 # Just waiting for new version to be released - self.votes.add(user, through_defaults={"support": support}) # type: ignore[arg-type,call-arg] + self.votes.add(user, through_defaults={"support": support}) # type: ignore[call-arg] @classmethod - def create_from_pr(cls, pr: dict[str, Any]) -> "tuple[PullRequest, Bill | None]": + def create_from_pr(cls, pr: dict[str, Any]) -> tuple[PullRequest, Self | None]: """Create a :class:`~democrasite.webiscite.models.PullRequest` and, if the creator has an account, :class:`~democrasite.webiscite.models.Bill` instance from a pull request @@ -227,7 +227,7 @@ def create_from_pr(cls, pr: dict[str, Any]) -> "tuple[PullRequest, Bill | None]" return pull_request, None # TODO: everything below here could be in BillManager - bill = Bill(**bill_kwargs) + bill = cls(**bill_kwargs) bill.full_clean() bill.save() logger.info("PR %s: Bill %s created", pr["number"], bill.id) diff --git a/democrasite/webiscite/views.py b/democrasite/webiscite/views.py index b9ec63b..63c389d 100644 --- a/democrasite/webiscite/views.py +++ b/democrasite/webiscite/views.py @@ -20,7 +20,7 @@ class BillListView(ListView): """View listing all open bills. Used for webiscite:index.""" model = Bill - queryset = Bill.open.all() # type: ignore [attr-defined] # comes from django_model_utils + queryset = Bill.open.all() # comes from django_model_utils def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) diff --git a/requirements/base.txt b/requirements/base.txt index 971d0e2..7c88ec4 100644 --- a/requirements/base.txt +++ b/requirements/base.txt @@ -21,6 +21,7 @@ django-redis==5.4.0 # https://github.com/jazzband/django-redis # Django REST Framework djangorestframework==3.14.0 # https://github.com/encode/django-rest-framework django-cors-headers==4.3.1 # https://github.com/adamchainz/django-cors-headers +dj-rest-auth==5.0.2 # https://github.com/iMerica/dj-rest-auth # DRF-spectacular for api documentation drf-spectacular==0.27.1 # https://github.com/tfranzel/drf-spectacular From aea7ae8cfa367a3b207d2e5eefa15501ecfff3ef Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 2 Mar 2024 18:59:00 -0500 Subject: [PATCH 02/11] Update frontend api --- .../api/auto/.openapi-generator-ignore | 1 + .../api/auto/.openapi-generator/FILES | 21 +- democrasite-frontend/api/auto/apis/ApiApi.ts | 519 -------- democrasite-frontend/api/auto/apis/AuthApi.ts | 393 +++++++ .../api/auto/apis/AuthTokenApi.ts | 105 -- .../api/auto/apis/AuthloginApi.ts | 74 ++ .../api/auto/apis/AuthlogoutApi.ts | 60 + .../api/auto/apis/AuthpasswordApi.ts | 162 +++ .../api/auto/apis/AuthuserApi.ts | 141 +++ .../api/auto/apis/BillsApi.ts | 181 +++ .../api/auto/apis/SchemaApi.ts | 179 +++ .../api/auto/apis/UsersApi.ts | 209 ++++ democrasite-frontend/api/auto/apis/index.ts | 10 +- democrasite-frontend/api/auto/models/Login.ts | 81 ++ .../api/auto/models/PasswordChange.ts | 74 ++ .../api/auto/models/PasswordReset.ts | 65 + .../api/auto/models/PasswordResetConfirm.ts | 92 ++ .../api/auto/models/PatchedUserDetails.ts | 92 ++ .../api/auto/models/RestAuthDetail.ts | 64 + .../api/auto/models/SocialLogin.ts | 80 ++ democrasite-frontend/api/auto/models/Token.ts | 65 + .../api/auto/models/UserDetails.ts | 97 ++ democrasite-frontend/api/auto/models/index.ts | 10 +- democrasite-frontend/api/auto/runtime.ts | 695 ++++++----- schema.json | 1043 +++++++++++++++-- 25 files changed, 3490 insertions(+), 1023 deletions(-) delete mode 100644 democrasite-frontend/api/auto/apis/ApiApi.ts create mode 100644 democrasite-frontend/api/auto/apis/AuthApi.ts delete mode 100644 democrasite-frontend/api/auto/apis/AuthTokenApi.ts create mode 100644 democrasite-frontend/api/auto/apis/AuthloginApi.ts create mode 100644 democrasite-frontend/api/auto/apis/AuthlogoutApi.ts create mode 100644 democrasite-frontend/api/auto/apis/AuthpasswordApi.ts create mode 100644 democrasite-frontend/api/auto/apis/AuthuserApi.ts create mode 100644 democrasite-frontend/api/auto/apis/BillsApi.ts create mode 100644 democrasite-frontend/api/auto/apis/SchemaApi.ts create mode 100644 democrasite-frontend/api/auto/apis/UsersApi.ts create mode 100644 democrasite-frontend/api/auto/models/Login.ts create mode 100644 democrasite-frontend/api/auto/models/PasswordChange.ts create mode 100644 democrasite-frontend/api/auto/models/PasswordReset.ts create mode 100644 democrasite-frontend/api/auto/models/PasswordResetConfirm.ts create mode 100644 democrasite-frontend/api/auto/models/PatchedUserDetails.ts create mode 100644 democrasite-frontend/api/auto/models/RestAuthDetail.ts create mode 100644 democrasite-frontend/api/auto/models/SocialLogin.ts create mode 100644 democrasite-frontend/api/auto/models/Token.ts create mode 100644 democrasite-frontend/api/auto/models/UserDetails.ts diff --git a/democrasite-frontend/api/auto/.openapi-generator-ignore b/democrasite-frontend/api/auto/.openapi-generator-ignore index 7484ee5..8904a39 100644 --- a/democrasite-frontend/api/auto/.openapi-generator-ignore +++ b/democrasite-frontend/api/auto/.openapi-generator-ignore @@ -3,6 +3,7 @@ # Use this file to prevent files from being overwritten by the generator. # The patterns follow closely to .gitignore or .dockerignore. +# Note that this should be avoided when possible to keep the API client in sync with the API definition. # As an example, the C# client generator defines ApiClient.cs. # You can make changes and tell OpenAPI Generator to ignore just this file by uncommenting the following line: diff --git a/democrasite-frontend/api/auto/.openapi-generator/FILES b/democrasite-frontend/api/auto/.openapi-generator/FILES index 214ee44..9b2a9d7 100644 --- a/democrasite-frontend/api/auto/.openapi-generator/FILES +++ b/democrasite-frontend/api/auto/.openapi-generator/FILES @@ -1,13 +1,26 @@ -.openapi-generator-ignore -apis/ApiApi.ts -apis/AuthTokenApi.ts +apis/AuthApi.ts +apis/AuthloginApi.ts +apis/AuthlogoutApi.ts +apis/AuthpasswordApi.ts +apis/AuthuserApi.ts +apis/BillsApi.ts +apis/SchemaApi.ts +apis/UsersApi.ts apis/index.ts index.ts -models/AuthToken.ts models/Bill.ts +models/Login.ts +models/PasswordChange.ts +models/PasswordReset.ts +models/PasswordResetConfirm.ts models/PatchedBill.ts models/PatchedUser.ts +models/PatchedUserDetails.ts models/PullRequest.ts +models/RestAuthDetail.ts +models/SocialLogin.ts +models/Token.ts models/User.ts +models/UserDetails.ts models/index.ts runtime.ts diff --git a/democrasite-frontend/api/auto/apis/ApiApi.ts b/democrasite-frontend/api/auto/apis/ApiApi.ts deleted file mode 100644 index 429a01f..0000000 --- a/democrasite-frontend/api/auto/apis/ApiApi.ts +++ /dev/null @@ -1,519 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - Bill, - PatchedBill, - PatchedUser, - User, -} from '../models/index'; -import { - BillFromJSON, - BillToJSON, - PatchedBillFromJSON, - PatchedBillToJSON, - PatchedUserFromJSON, - PatchedUserToJSON, - UserFromJSON, - UserToJSON, -} from '../models/index'; - -export interface ApiBillsPartialUpdateRequest { - id: number; - patchedBill?: PatchedBill; -} - -export interface ApiBillsRetrieveRequest { - id: number; -} - -export interface ApiBillsUpdateRequest { - id: number; - bill: Bill; -} - -export interface ApiSchemaRetrieveRequest { - format?: ApiSchemaRetrieveFormatEnum; - lang?: ApiSchemaRetrieveLangEnum; -} - -export interface ApiUsersPartialUpdateRequest { - username: string; - patchedUser?: PatchedUser; -} - -export interface ApiUsersRetrieveRequest { - username: string; -} - -export interface ApiUsersUpdateRequest { - username: string; - user: User; -} - -/** - * - */ -export class ApiApi extends runtime.BaseAPI { - - /** - */ - async apiBillsListRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise>> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/bills/`, - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => jsonValue.map(BillFromJSON)); - } - - /** - */ - async apiBillsList(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const response = await this.apiBillsListRaw(initOverrides); - return await response.value(); - } - - /** - */ - async apiBillsPartialUpdateRaw(requestParameters: ApiBillsPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.id === null || requestParameters.id === undefined) { - throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling apiBillsPartialUpdate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), - method: 'PATCH', - headers: headerParameters, - query: queryParameters, - body: PatchedBillToJSON(requestParameters.patchedBill), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); - } - - /** - */ - async apiBillsPartialUpdate(requestParameters: ApiBillsPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiBillsPartialUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - */ - async apiBillsRetrieveRaw(requestParameters: ApiBillsRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.id === null || requestParameters.id === undefined) { - throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling apiBillsRetrieve.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); - } - - /** - */ - async apiBillsRetrieve(requestParameters: ApiBillsRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiBillsRetrieveRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - */ - async apiBillsUpdateRaw(requestParameters: ApiBillsUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.id === null || requestParameters.id === undefined) { - throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling apiBillsUpdate.'); - } - - if (requestParameters.bill === null || requestParameters.bill === undefined) { - throw new runtime.RequiredError('bill','Required parameter requestParameters.bill was null or undefined when calling apiBillsUpdate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), - method: 'PUT', - headers: headerParameters, - query: queryParameters, - body: BillToJSON(requestParameters.bill), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); - } - - /** - */ - async apiBillsUpdate(requestParameters: ApiBillsUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiBillsUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - * OpenApi3 schema for this API. Format can be selected via content negotiation. - YAML: application/vnd.oai.openapi - JSON: application/vnd.oai.openapi+json - */ - async apiSchemaRetrieveRaw(requestParameters: ApiSchemaRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const queryParameters: any = {}; - - if (requestParameters.format !== undefined) { - queryParameters['format'] = requestParameters.format; - } - - if (requestParameters.lang !== undefined) { - queryParameters['lang'] = requestParameters.lang; - } - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/schema/`, - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response); - } - - /** - * OpenApi3 schema for this API. Format can be selected via content negotiation. - YAML: application/vnd.oai.openapi - JSON: application/vnd.oai.openapi+json - */ - async apiSchemaRetrieve(requestParameters: ApiSchemaRetrieveRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise<{ [key: string]: any; }> { - const response = await this.apiSchemaRetrieveRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - */ - async apiUsersListRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise>> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/users/`, - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => jsonValue.map(UserFromJSON)); - } - - /** - */ - async apiUsersList(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const response = await this.apiUsersListRaw(initOverrides); - return await response.value(); - } - - /** - */ - async apiUsersMeRetrieveRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/users/me/`, - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); - } - - /** - */ - async apiUsersMeRetrieve(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiUsersMeRetrieveRaw(initOverrides); - return await response.value(); - } - - /** - */ - async apiUsersPartialUpdateRaw(requestParameters: ApiUsersPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.username === null || requestParameters.username === undefined) { - throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling apiUsersPartialUpdate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), - method: 'PATCH', - headers: headerParameters, - query: queryParameters, - body: PatchedUserToJSON(requestParameters.patchedUser), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); - } - - /** - */ - async apiUsersPartialUpdate(requestParameters: ApiUsersPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiUsersPartialUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - */ - async apiUsersRetrieveRaw(requestParameters: ApiUsersRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.username === null || requestParameters.username === undefined) { - throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling apiUsersRetrieve.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); - } - - /** - */ - async apiUsersRetrieve(requestParameters: ApiUsersRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiUsersRetrieveRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - */ - async apiUsersUpdateRaw(requestParameters: ApiUsersUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.username === null || requestParameters.username === undefined) { - throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling apiUsersUpdate.'); - } - - if (requestParameters.user === null || requestParameters.user === undefined) { - throw new runtime.RequiredError('user','Required parameter requestParameters.user was null or undefined when calling apiUsersUpdate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), - method: 'PUT', - headers: headerParameters, - query: queryParameters, - body: UserToJSON(requestParameters.user), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); - } - - /** - */ - async apiUsersUpdate(requestParameters: ApiUsersUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.apiUsersUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - -} - -/** - * @export - */ -export const ApiSchemaRetrieveFormatEnum = { - Json: 'json', - Yaml: 'yaml' -} as const; -export type ApiSchemaRetrieveFormatEnum = typeof ApiSchemaRetrieveFormatEnum[keyof typeof ApiSchemaRetrieveFormatEnum]; -/** - * @export - */ -export const ApiSchemaRetrieveLangEnum = { - Af: 'af', - Ar: 'ar', - ArDz: 'ar-dz', - Ast: 'ast', - Az: 'az', - Be: 'be', - Bg: 'bg', - Bn: 'bn', - Br: 'br', - Bs: 'bs', - Ca: 'ca', - Ckb: 'ckb', - Cs: 'cs', - Cy: 'cy', - Da: 'da', - De: 'de', - Dsb: 'dsb', - El: 'el', - En: 'en', - EnAu: 'en-au', - EnGb: 'en-gb', - Eo: 'eo', - Es: 'es', - EsAr: 'es-ar', - EsCo: 'es-co', - EsMx: 'es-mx', - EsNi: 'es-ni', - EsVe: 'es-ve', - Et: 'et', - Eu: 'eu', - Fa: 'fa', - Fi: 'fi', - Fr: 'fr', - Fy: 'fy', - Ga: 'ga', - Gd: 'gd', - Gl: 'gl', - He: 'he', - Hi: 'hi', - Hr: 'hr', - Hsb: 'hsb', - Hu: 'hu', - Hy: 'hy', - Ia: 'ia', - Id: 'id', - Ig: 'ig', - Io: 'io', - Is: 'is', - It: 'it', - Ja: 'ja', - Ka: 'ka', - Kab: 'kab', - Kk: 'kk', - Km: 'km', - Kn: 'kn', - Ko: 'ko', - Ky: 'ky', - Lb: 'lb', - Lt: 'lt', - Lv: 'lv', - Mk: 'mk', - Ml: 'ml', - Mn: 'mn', - Mr: 'mr', - Ms: 'ms', - My: 'my', - Nb: 'nb', - Ne: 'ne', - Nl: 'nl', - Nn: 'nn', - Os: 'os', - Pa: 'pa', - Pl: 'pl', - Pt: 'pt', - PtBr: 'pt-br', - Ro: 'ro', - Ru: 'ru', - Sk: 'sk', - Sl: 'sl', - Sq: 'sq', - Sr: 'sr', - SrLatn: 'sr-latn', - Sv: 'sv', - Sw: 'sw', - Ta: 'ta', - Te: 'te', - Tg: 'tg', - Th: 'th', - Tk: 'tk', - Tr: 'tr', - Tt: 'tt', - Udm: 'udm', - Uk: 'uk', - Ur: 'ur', - Uz: 'uz', - Vi: 'vi', - ZhHans: 'zh-hans', - ZhHant: 'zh-hant' -} as const; -export type ApiSchemaRetrieveLangEnum = typeof ApiSchemaRetrieveLangEnum[keyof typeof ApiSchemaRetrieveLangEnum]; diff --git a/democrasite-frontend/api/auto/apis/AuthApi.ts b/democrasite-frontend/api/auto/apis/AuthApi.ts new file mode 100644 index 0000000..bf2ff40 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/AuthApi.ts @@ -0,0 +1,393 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + Login, + PasswordChange, + PasswordReset, + PasswordResetConfirm, + PatchedUserDetails, + RestAuthDetail, + SocialLogin, + Token, + UserDetails, +} from '../models/index'; +import { + LoginFromJSON, + LoginToJSON, + PasswordChangeFromJSON, + PasswordChangeToJSON, + PasswordResetFromJSON, + PasswordResetToJSON, + PasswordResetConfirmFromJSON, + PasswordResetConfirmToJSON, + PatchedUserDetailsFromJSON, + PatchedUserDetailsToJSON, + RestAuthDetailFromJSON, + RestAuthDetailToJSON, + SocialLoginFromJSON, + SocialLoginToJSON, + TokenFromJSON, + TokenToJSON, + UserDetailsFromJSON, + UserDetailsToJSON, +} from '../models/index'; + +export interface AuthGithubCreateRequest { + socialLogin?: SocialLogin; +} + +export interface AuthLoginCreateRequest { + login: Login; +} + +export interface AuthPasswordChangeCreateRequest { + passwordChange: PasswordChange; +} + +export interface AuthPasswordResetConfirmCreateRequest { + passwordResetConfirm: PasswordResetConfirm; +} + +export interface AuthPasswordResetCreateRequest { + passwordReset: PasswordReset; +} + +export interface AuthUserPartialUpdateRequest { + patchedUserDetails?: PatchedUserDetails; +} + +export interface AuthUserUpdateRequest { + userDetails: UserDetails; +} + +/** + * + */ +export class AuthApi extends runtime.BaseAPI { + + /** + * class used for social authentications example usage for facebook with access_token ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter ------------- example usage for facebook with code ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter from allauth.socialaccount.providers.oauth2.client import OAuth2Client class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter client_class = OAuth2Client callback_url = \'localhost:8000\' ------------- + */ + async authGithubCreateRaw(requestParameters: AuthGithubCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/github/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: SocialLoginToJSON(requestParameters.socialLogin), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => SocialLoginFromJSON(jsonValue)); + } + + /** + * class used for social authentications example usage for facebook with access_token ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter ------------- example usage for facebook with code ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter from allauth.socialaccount.providers.oauth2.client import OAuth2Client class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter client_class = OAuth2Client callback_url = \'localhost:8000\' ------------- + */ + async authGithubCreate(requestParameters: AuthGithubCreateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authGithubCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. + */ + async authLoginCreateRaw(requestParameters: AuthLoginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.login === null || requestParameters.login === undefined) { + throw new runtime.RequiredError('login','Required parameter requestParameters.login was null or undefined when calling authLoginCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/login/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: LoginToJSON(requestParameters.login), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => TokenFromJSON(jsonValue)); + } + + /** + * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. + */ + async authLoginCreate(requestParameters: AuthLoginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authLoginCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. + */ + async authLogoutCreateRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/logout/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. + */ + async authLogoutCreate(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authLogoutCreateRaw(initOverrides); + return await response.value(); + } + + /** + * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. + */ + async authPasswordChangeCreateRaw(requestParameters: AuthPasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordChange === null || requestParameters.passwordChange === undefined) { + throw new runtime.RequiredError('passwordChange','Required parameter requestParameters.passwordChange was null or undefined when calling authPasswordChangeCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/password/change/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordChangeToJSON(requestParameters.passwordChange), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. + */ + async authPasswordChangeCreate(requestParameters: AuthPasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authPasswordChangeCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. + */ + async authPasswordResetConfirmCreateRaw(requestParameters: AuthPasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordResetConfirm === null || requestParameters.passwordResetConfirm === undefined) { + throw new runtime.RequiredError('passwordResetConfirm','Required parameter requestParameters.passwordResetConfirm was null or undefined when calling authPasswordResetConfirmCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/password/reset/confirm/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordResetConfirmToJSON(requestParameters.passwordResetConfirm), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. + */ + async authPasswordResetConfirmCreate(requestParameters: AuthPasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authPasswordResetConfirmCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. + */ + async authPasswordResetCreateRaw(requestParameters: AuthPasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordReset === null || requestParameters.passwordReset === undefined) { + throw new runtime.RequiredError('passwordReset','Required parameter requestParameters.passwordReset was null or undefined when calling authPasswordResetCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/password/reset/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordResetToJSON(requestParameters.passwordReset), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. + */ + async authPasswordResetCreate(requestParameters: AuthPasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authPasswordResetCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserPartialUpdateRaw(requestParameters: AuthUserPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/user/`, + method: 'PATCH', + headers: headerParameters, + query: queryParameters, + body: PatchedUserDetailsToJSON(requestParameters.patchedUserDetails), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserPartialUpdate(requestParameters: AuthUserPartialUpdateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authUserPartialUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserRetrieveRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/user/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserRetrieve(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authUserRetrieveRaw(initOverrides); + return await response.value(); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserUpdateRaw(requestParameters: AuthUserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.userDetails === null || requestParameters.userDetails === undefined) { + throw new runtime.RequiredError('userDetails','Required parameter requestParameters.userDetails was null or undefined when calling authUserUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/auth/user/`, + method: 'PUT', + headers: headerParameters, + query: queryParameters, + body: UserDetailsToJSON(requestParameters.userDetails), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authUserUpdate(requestParameters: AuthUserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authUserUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/AuthTokenApi.ts b/democrasite-frontend/api/auto/apis/AuthTokenApi.ts deleted file mode 100644 index 7b897cc..0000000 --- a/democrasite-frontend/api/auto/apis/AuthTokenApi.ts +++ /dev/null @@ -1,105 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - AuthToken, -} from '../models/index'; -import { - AuthTokenFromJSON, - AuthTokenToJSON, -} from '../models/index'; - -export interface AuthTokenCreateRequest { - username: string; - password: string; - token: string; -} - -/** - * - */ -export class AuthTokenApi extends runtime.BaseAPI { - - /** - */ - async authTokenCreateRaw(requestParameters: AuthTokenCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.username === null || requestParameters.username === undefined) { - throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling authTokenCreate.'); - } - - if (requestParameters.password === null || requestParameters.password === undefined) { - throw new runtime.RequiredError('password','Required parameter requestParameters.password was null or undefined when calling authTokenCreate.'); - } - - if (requestParameters.token === null || requestParameters.token === undefined) { - throw new runtime.RequiredError('token','Required parameter requestParameters.token was null or undefined when calling authTokenCreate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const consumes: runtime.Consume[] = [ - { contentType: 'application/x-www-form-urlencoded' }, - { contentType: 'multipart/form-data' }, - { contentType: 'application/json' }, - ]; - // @ts-ignore: canConsumeForm may be unused - const canConsumeForm = runtime.canConsumeForm(consumes); - - let formParams: { append(param: string, value: any): any }; - let useForm = false; - if (useForm) { - formParams = new FormData(); - } else { - formParams = new URLSearchParams(); - } - - if (requestParameters.username !== undefined) { - formParams.append('username', requestParameters.username as any); - } - - if (requestParameters.password !== undefined) { - formParams.append('password', requestParameters.password as any); - } - - if (requestParameters.token !== undefined) { - formParams.append('token', requestParameters.token as any); - } - - const response = await this.request({ - path: `/auth-token/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - body: formParams, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => AuthTokenFromJSON(jsonValue)); - } - - /** - */ - async authTokenCreate(requestParameters: AuthTokenCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authTokenCreateRaw(requestParameters, initOverrides); - return await response.value(); - } - -} diff --git a/democrasite-frontend/api/auto/apis/AuthloginApi.ts b/democrasite-frontend/api/auto/apis/AuthloginApi.ts new file mode 100644 index 0000000..dbaf9aa --- /dev/null +++ b/democrasite-frontend/api/auto/apis/AuthloginApi.ts @@ -0,0 +1,74 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + Login, + Token, +} from '../models/index'; +import { + LoginFromJSON, + LoginToJSON, + TokenFromJSON, + TokenToJSON, +} from '../models/index'; + +export interface AuthloginCreateRequest { + login: Login; +} + +/** + * + */ +export class AuthloginApi extends runtime.BaseAPI { + + /** + * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. + */ + async authloginCreateRaw(requestParameters: AuthloginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.login === null || requestParameters.login === undefined) { + throw new runtime.RequiredError('login','Required parameter requestParameters.login was null or undefined when calling authloginCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authlogin/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: LoginToJSON(requestParameters.login), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => TokenFromJSON(jsonValue)); + } + + /** + * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. + */ + async authloginCreate(requestParameters: AuthloginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authloginCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/AuthlogoutApi.ts b/democrasite-frontend/api/auto/apis/AuthlogoutApi.ts new file mode 100644 index 0000000..f229ad8 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/AuthlogoutApi.ts @@ -0,0 +1,60 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + RestAuthDetail, +} from '../models/index'; +import { + RestAuthDetailFromJSON, + RestAuthDetailToJSON, +} from '../models/index'; + +/** + * + */ +export class AuthlogoutApi extends runtime.BaseAPI { + + /** + * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. + */ + async authlogoutCreateRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authlogout/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. + */ + async authlogoutCreate(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authlogoutCreateRaw(initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/AuthpasswordApi.ts b/democrasite-frontend/api/auto/apis/AuthpasswordApi.ts new file mode 100644 index 0000000..03131c0 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/AuthpasswordApi.ts @@ -0,0 +1,162 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + PasswordChange, + PasswordReset, + PasswordResetConfirm, + RestAuthDetail, +} from '../models/index'; +import { + PasswordChangeFromJSON, + PasswordChangeToJSON, + PasswordResetFromJSON, + PasswordResetToJSON, + PasswordResetConfirmFromJSON, + PasswordResetConfirmToJSON, + RestAuthDetailFromJSON, + RestAuthDetailToJSON, +} from '../models/index'; + +export interface AuthpasswordChangeCreateRequest { + passwordChange: PasswordChange; +} + +export interface AuthpasswordResetConfirmCreateRequest { + passwordResetConfirm: PasswordResetConfirm; +} + +export interface AuthpasswordResetCreateRequest { + passwordReset: PasswordReset; +} + +/** + * + */ +export class AuthpasswordApi extends runtime.BaseAPI { + + /** + * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. + */ + async authpasswordChangeCreateRaw(requestParameters: AuthpasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordChange === null || requestParameters.passwordChange === undefined) { + throw new runtime.RequiredError('passwordChange','Required parameter requestParameters.passwordChange was null or undefined when calling authpasswordChangeCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authpassword/change/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordChangeToJSON(requestParameters.passwordChange), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. + */ + async authpasswordChangeCreate(requestParameters: AuthpasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authpasswordChangeCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. + */ + async authpasswordResetConfirmCreateRaw(requestParameters: AuthpasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordResetConfirm === null || requestParameters.passwordResetConfirm === undefined) { + throw new runtime.RequiredError('passwordResetConfirm','Required parameter requestParameters.passwordResetConfirm was null or undefined when calling authpasswordResetConfirmCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authpassword/reset/confirm/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordResetConfirmToJSON(requestParameters.passwordResetConfirm), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. + */ + async authpasswordResetConfirmCreate(requestParameters: AuthpasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authpasswordResetConfirmCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. + */ + async authpasswordResetCreateRaw(requestParameters: AuthpasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.passwordReset === null || requestParameters.passwordReset === undefined) { + throw new runtime.RequiredError('passwordReset','Required parameter requestParameters.passwordReset was null or undefined when calling authpasswordResetCreate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authpassword/reset/`, + method: 'POST', + headers: headerParameters, + query: queryParameters, + body: PasswordResetToJSON(requestParameters.passwordReset), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); + } + + /** + * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. + */ + async authpasswordResetCreate(requestParameters: AuthpasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authpasswordResetCreateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/AuthuserApi.ts b/democrasite-frontend/api/auto/apis/AuthuserApi.ts new file mode 100644 index 0000000..c2c2728 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/AuthuserApi.ts @@ -0,0 +1,141 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + PatchedUserDetails, + UserDetails, +} from '../models/index'; +import { + PatchedUserDetailsFromJSON, + PatchedUserDetailsToJSON, + UserDetailsFromJSON, + UserDetailsToJSON, +} from '../models/index'; + +export interface AuthuserPartialUpdateRequest { + patchedUserDetails?: PatchedUserDetails; +} + +export interface AuthuserUpdateRequest { + userDetails: UserDetails; +} + +/** + * + */ +export class AuthuserApi extends runtime.BaseAPI { + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserPartialUpdateRaw(requestParameters: AuthuserPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authuser/`, + method: 'PATCH', + headers: headerParameters, + query: queryParameters, + body: PatchedUserDetailsToJSON(requestParameters.patchedUserDetails), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserPartialUpdate(requestParameters: AuthuserPartialUpdateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authuserPartialUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserRetrieveRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authuser/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserRetrieve(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authuserRetrieveRaw(initOverrides); + return await response.value(); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserUpdateRaw(requestParameters: AuthuserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.userDetails === null || requestParameters.userDetails === undefined) { + throw new runtime.RequiredError('userDetails','Required parameter requestParameters.userDetails was null or undefined when calling authuserUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/authuser/`, + method: 'PUT', + headers: headerParameters, + query: queryParameters, + body: UserDetailsToJSON(requestParameters.userDetails), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); + } + + /** + * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. + */ + async authuserUpdate(requestParameters: AuthuserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.authuserUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/BillsApi.ts b/democrasite-frontend/api/auto/apis/BillsApi.ts new file mode 100644 index 0000000..2f3d867 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/BillsApi.ts @@ -0,0 +1,181 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + Bill, + PatchedBill, +} from '../models/index'; +import { + BillFromJSON, + BillToJSON, + PatchedBillFromJSON, + PatchedBillToJSON, +} from '../models/index'; + +export interface BillsPartialUpdateRequest { + id: number; + patchedBill?: PatchedBill; +} + +export interface BillsRetrieveRequest { + id: number; +} + +export interface BillsUpdateRequest { + id: number; + bill: Bill; +} + +/** + * + */ +export class BillsApi extends runtime.BaseAPI { + + /** + */ + async billsListRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise>> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/bills/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => jsonValue.map(BillFromJSON)); + } + + /** + */ + async billsList(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const response = await this.billsListRaw(initOverrides); + return await response.value(); + } + + /** + */ + async billsPartialUpdateRaw(requestParameters: BillsPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.id === null || requestParameters.id === undefined) { + throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling billsPartialUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), + method: 'PATCH', + headers: headerParameters, + query: queryParameters, + body: PatchedBillToJSON(requestParameters.patchedBill), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); + } + + /** + */ + async billsPartialUpdate(requestParameters: BillsPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.billsPartialUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + */ + async billsRetrieveRaw(requestParameters: BillsRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.id === null || requestParameters.id === undefined) { + throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling billsRetrieve.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); + } + + /** + */ + async billsRetrieve(requestParameters: BillsRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.billsRetrieveRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + */ + async billsUpdateRaw(requestParameters: BillsUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.id === null || requestParameters.id === undefined) { + throw new runtime.RequiredError('id','Required parameter requestParameters.id was null or undefined when calling billsUpdate.'); + } + + if (requestParameters.bill === null || requestParameters.bill === undefined) { + throw new runtime.RequiredError('bill','Required parameter requestParameters.bill was null or undefined when calling billsUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/bills/{id}/`.replace(`{${"id"}}`, encodeURIComponent(String(requestParameters.id))), + method: 'PUT', + headers: headerParameters, + query: queryParameters, + body: BillToJSON(requestParameters.bill), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => BillFromJSON(jsonValue)); + } + + /** + */ + async billsUpdate(requestParameters: BillsUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.billsUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/SchemaApi.ts b/democrasite-frontend/api/auto/apis/SchemaApi.ts new file mode 100644 index 0000000..e90369f --- /dev/null +++ b/democrasite-frontend/api/auto/apis/SchemaApi.ts @@ -0,0 +1,179 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; + +export interface SchemaRetrieveRequest { + format?: SchemaRetrieveFormatEnum; + lang?: SchemaRetrieveLangEnum; +} + +/** + * + */ +export class SchemaApi extends runtime.BaseAPI { + + /** + * OpenApi3 schema for this API. Format can be selected via content negotiation. - YAML: application/vnd.oai.openapi - JSON: application/vnd.oai.openapi+json + */ + async schemaRetrieveRaw(requestParameters: SchemaRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + if (requestParameters.format !== undefined) { + queryParameters['format'] = requestParameters.format; + } + + if (requestParameters.lang !== undefined) { + queryParameters['lang'] = requestParameters.lang; + } + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/schema/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response); + } + + /** + * OpenApi3 schema for this API. Format can be selected via content negotiation. - YAML: application/vnd.oai.openapi - JSON: application/vnd.oai.openapi+json + */ + async schemaRetrieve(requestParameters: SchemaRetrieveRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise<{ [key: string]: any; }> { + const response = await this.schemaRetrieveRaw(requestParameters, initOverrides); + return await response.value(); + } + +} + +/** + * @export + */ +export const SchemaRetrieveFormatEnum = { + Json: 'json', + Yaml: 'yaml' +} as const; +export type SchemaRetrieveFormatEnum = typeof SchemaRetrieveFormatEnum[keyof typeof SchemaRetrieveFormatEnum]; +/** + * @export + */ +export const SchemaRetrieveLangEnum = { + Af: 'af', + Ar: 'ar', + ArDz: 'ar-dz', + Ast: 'ast', + Az: 'az', + Be: 'be', + Bg: 'bg', + Bn: 'bn', + Br: 'br', + Bs: 'bs', + Ca: 'ca', + Ckb: 'ckb', + Cs: 'cs', + Cy: 'cy', + Da: 'da', + De: 'de', + Dsb: 'dsb', + El: 'el', + En: 'en', + EnAu: 'en-au', + EnGb: 'en-gb', + Eo: 'eo', + Es: 'es', + EsAr: 'es-ar', + EsCo: 'es-co', + EsMx: 'es-mx', + EsNi: 'es-ni', + EsVe: 'es-ve', + Et: 'et', + Eu: 'eu', + Fa: 'fa', + Fi: 'fi', + Fr: 'fr', + Fy: 'fy', + Ga: 'ga', + Gd: 'gd', + Gl: 'gl', + He: 'he', + Hi: 'hi', + Hr: 'hr', + Hsb: 'hsb', + Hu: 'hu', + Hy: 'hy', + Ia: 'ia', + Id: 'id', + Ig: 'ig', + Io: 'io', + Is: 'is', + It: 'it', + Ja: 'ja', + Ka: 'ka', + Kab: 'kab', + Kk: 'kk', + Km: 'km', + Kn: 'kn', + Ko: 'ko', + Ky: 'ky', + Lb: 'lb', + Lt: 'lt', + Lv: 'lv', + Mk: 'mk', + Ml: 'ml', + Mn: 'mn', + Mr: 'mr', + Ms: 'ms', + My: 'my', + Nb: 'nb', + Ne: 'ne', + Nl: 'nl', + Nn: 'nn', + Os: 'os', + Pa: 'pa', + Pl: 'pl', + Pt: 'pt', + PtBr: 'pt-br', + Ro: 'ro', + Ru: 'ru', + Sk: 'sk', + Sl: 'sl', + Sq: 'sq', + Sr: 'sr', + SrLatn: 'sr-latn', + Sv: 'sv', + Sw: 'sw', + Ta: 'ta', + Te: 'te', + Tg: 'tg', + Th: 'th', + Tk: 'tk', + Tr: 'tr', + Tt: 'tt', + Udm: 'udm', + Uk: 'uk', + Ur: 'ur', + Uz: 'uz', + Vi: 'vi', + ZhHans: 'zh-hans', + ZhHant: 'zh-hant' +} as const; +export type SchemaRetrieveLangEnum = typeof SchemaRetrieveLangEnum[keyof typeof SchemaRetrieveLangEnum]; diff --git a/democrasite-frontend/api/auto/apis/UsersApi.ts b/democrasite-frontend/api/auto/apis/UsersApi.ts new file mode 100644 index 0000000..4cb1500 --- /dev/null +++ b/democrasite-frontend/api/auto/apis/UsersApi.ts @@ -0,0 +1,209 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + + +import * as runtime from '../runtime'; +import type { + PatchedUser, + User, +} from '../models/index'; +import { + PatchedUserFromJSON, + PatchedUserToJSON, + UserFromJSON, + UserToJSON, +} from '../models/index'; + +export interface UsersPartialUpdateRequest { + username: string; + patchedUser?: PatchedUser; +} + +export interface UsersRetrieveRequest { + username: string; +} + +export interface UsersUpdateRequest { + username: string; + user: User; +} + +/** + * + */ +export class UsersApi extends runtime.BaseAPI { + + /** + */ + async usersListRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise>> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/users/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => jsonValue.map(UserFromJSON)); + } + + /** + */ + async usersList(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const response = await this.usersListRaw(initOverrides); + return await response.value(); + } + + /** + */ + async usersMeRetrieveRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/users/me/`, + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); + } + + /** + */ + async usersMeRetrieve(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.usersMeRetrieveRaw(initOverrides); + return await response.value(); + } + + /** + */ + async usersPartialUpdateRaw(requestParameters: UsersPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.username === null || requestParameters.username === undefined) { + throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling usersPartialUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), + method: 'PATCH', + headers: headerParameters, + query: queryParameters, + body: PatchedUserToJSON(requestParameters.patchedUser), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); + } + + /** + */ + async usersPartialUpdate(requestParameters: UsersPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.usersPartialUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + */ + async usersRetrieveRaw(requestParameters: UsersRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.username === null || requestParameters.username === undefined) { + throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling usersRetrieve.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), + method: 'GET', + headers: headerParameters, + query: queryParameters, + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); + } + + /** + */ + async usersRetrieve(requestParameters: UsersRetrieveRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.usersRetrieveRaw(requestParameters, initOverrides); + return await response.value(); + } + + /** + */ + async usersUpdateRaw(requestParameters: UsersUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + if (requestParameters.username === null || requestParameters.username === undefined) { + throw new runtime.RequiredError('username','Required parameter requestParameters.username was null or undefined when calling usersUpdate.'); + } + + if (requestParameters.user === null || requestParameters.user === undefined) { + throw new runtime.RequiredError('user','Required parameter requestParameters.user was null or undefined when calling usersUpdate.'); + } + + const queryParameters: any = {}; + + const headerParameters: runtime.HTTPHeaders = {}; + + headerParameters['Content-Type'] = 'application/json'; + + if (this.configuration && this.configuration.apiKey) { + headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication + } + + const response = await this.request({ + path: `/api/users/{username}/`.replace(`{${"username"}}`, encodeURIComponent(String(requestParameters.username))), + method: 'PUT', + headers: headerParameters, + query: queryParameters, + body: UserToJSON(requestParameters.user), + }, initOverrides); + + return new runtime.JSONApiResponse(response, (jsonValue) => UserFromJSON(jsonValue)); + } + + /** + */ + async usersUpdate(requestParameters: UsersUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + const response = await this.usersUpdateRaw(requestParameters, initOverrides); + return await response.value(); + } + +} diff --git a/democrasite-frontend/api/auto/apis/index.ts b/democrasite-frontend/api/auto/apis/index.ts index bec1e8f..5d1cdf3 100644 --- a/democrasite-frontend/api/auto/apis/index.ts +++ b/democrasite-frontend/api/auto/apis/index.ts @@ -1,4 +1,10 @@ /* tslint:disable */ /* eslint-disable */ -export * from './ApiApi'; -export * from './AuthTokenApi'; +export * from './AuthApi'; +export * from './AuthloginApi'; +export * from './AuthlogoutApi'; +export * from './AuthpasswordApi'; +export * from './AuthuserApi'; +export * from './BillsApi'; +export * from './SchemaApi'; +export * from './UsersApi'; diff --git a/democrasite-frontend/api/auto/models/Login.ts b/democrasite-frontend/api/auto/models/Login.ts new file mode 100644 index 0000000..29c462a --- /dev/null +++ b/democrasite-frontend/api/auto/models/Login.ts @@ -0,0 +1,81 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * + * @export + * @interface Login + */ +export interface Login { + /** + * + * @type {string} + * @memberof Login + */ + username?: string; + /** + * + * @type {string} + * @memberof Login + */ + email?: string; + /** + * + * @type {string} + * @memberof Login + */ + password: string; +} + +/** + * Check if a given object implements the Login interface. + */ +export function instanceOfLogin(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "password" in value; + + return isInstance; +} + +export function LoginFromJSON(json: any): Login { + return LoginFromJSONTyped(json, false); +} + +export function LoginFromJSONTyped(json: any, ignoreDiscriminator: boolean): Login { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'username': !exists(json, 'username') ? undefined : json['username'], + 'email': !exists(json, 'email') ? undefined : json['email'], + 'password': json['password'], + }; +} + +export function LoginToJSON(value?: Login | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'username': value.username, + 'email': value.email, + 'password': value.password, + }; +} diff --git a/democrasite-frontend/api/auto/models/PasswordChange.ts b/democrasite-frontend/api/auto/models/PasswordChange.ts new file mode 100644 index 0000000..fc8749f --- /dev/null +++ b/democrasite-frontend/api/auto/models/PasswordChange.ts @@ -0,0 +1,74 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * + * @export + * @interface PasswordChange + */ +export interface PasswordChange { + /** + * + * @type {string} + * @memberof PasswordChange + */ + newPassword1: string; + /** + * + * @type {string} + * @memberof PasswordChange + */ + newPassword2: string; +} + +/** + * Check if a given object implements the PasswordChange interface. + */ +export function instanceOfPasswordChange(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "newPassword1" in value; + isInstance = isInstance && "newPassword2" in value; + + return isInstance; +} + +export function PasswordChangeFromJSON(json: any): PasswordChange { + return PasswordChangeFromJSONTyped(json, false); +} + +export function PasswordChangeFromJSONTyped(json: any, ignoreDiscriminator: boolean): PasswordChange { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'newPassword1': json['new_password1'], + 'newPassword2': json['new_password2'], + }; +} + +export function PasswordChangeToJSON(value?: PasswordChange | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'new_password1': value.newPassword1, + 'new_password2': value.newPassword2, + }; +} diff --git a/democrasite-frontend/api/auto/models/PasswordReset.ts b/democrasite-frontend/api/auto/models/PasswordReset.ts new file mode 100644 index 0000000..5b2aec5 --- /dev/null +++ b/democrasite-frontend/api/auto/models/PasswordReset.ts @@ -0,0 +1,65 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * Serializer for requesting a password reset e-mail. + * @export + * @interface PasswordReset + */ +export interface PasswordReset { + /** + * + * @type {string} + * @memberof PasswordReset + */ + email: string; +} + +/** + * Check if a given object implements the PasswordReset interface. + */ +export function instanceOfPasswordReset(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "email" in value; + + return isInstance; +} + +export function PasswordResetFromJSON(json: any): PasswordReset { + return PasswordResetFromJSONTyped(json, false); +} + +export function PasswordResetFromJSONTyped(json: any, ignoreDiscriminator: boolean): PasswordReset { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'email': json['email'], + }; +} + +export function PasswordResetToJSON(value?: PasswordReset | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'email': value.email, + }; +} diff --git a/democrasite-frontend/api/auto/models/PasswordResetConfirm.ts b/democrasite-frontend/api/auto/models/PasswordResetConfirm.ts new file mode 100644 index 0000000..c53b68c --- /dev/null +++ b/democrasite-frontend/api/auto/models/PasswordResetConfirm.ts @@ -0,0 +1,92 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * Serializer for confirming a password reset attempt. + * @export + * @interface PasswordResetConfirm + */ +export interface PasswordResetConfirm { + /** + * + * @type {string} + * @memberof PasswordResetConfirm + */ + newPassword1: string; + /** + * + * @type {string} + * @memberof PasswordResetConfirm + */ + newPassword2: string; + /** + * + * @type {string} + * @memberof PasswordResetConfirm + */ + uid: string; + /** + * + * @type {string} + * @memberof PasswordResetConfirm + */ + token: string; +} + +/** + * Check if a given object implements the PasswordResetConfirm interface. + */ +export function instanceOfPasswordResetConfirm(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "newPassword1" in value; + isInstance = isInstance && "newPassword2" in value; + isInstance = isInstance && "uid" in value; + isInstance = isInstance && "token" in value; + + return isInstance; +} + +export function PasswordResetConfirmFromJSON(json: any): PasswordResetConfirm { + return PasswordResetConfirmFromJSONTyped(json, false); +} + +export function PasswordResetConfirmFromJSONTyped(json: any, ignoreDiscriminator: boolean): PasswordResetConfirm { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'newPassword1': json['new_password1'], + 'newPassword2': json['new_password2'], + 'uid': json['uid'], + 'token': json['token'], + }; +} + +export function PasswordResetConfirmToJSON(value?: PasswordResetConfirm | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'new_password1': value.newPassword1, + 'new_password2': value.newPassword2, + 'uid': value.uid, + 'token': value.token, + }; +} diff --git a/democrasite-frontend/api/auto/models/PatchedUserDetails.ts b/democrasite-frontend/api/auto/models/PatchedUserDetails.ts new file mode 100644 index 0000000..107041e --- /dev/null +++ b/democrasite-frontend/api/auto/models/PatchedUserDetails.ts @@ -0,0 +1,92 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * User model w/o password + * @export + * @interface PatchedUserDetails + */ +export interface PatchedUserDetails { + /** + * + * @type {number} + * @memberof PatchedUserDetails + */ + readonly pk?: number; + /** + * Required. 150 characters or fewer. Letters, digits and @/./+/-/_ only. + * @type {string} + * @memberof PatchedUserDetails + */ + username?: string; + /** + * + * @type {string} + * @memberof PatchedUserDetails + */ + readonly email?: string; + /** + * + * @type {string} + * @memberof PatchedUserDetails + */ + readonly firstName?: string; + /** + * + * @type {string} + * @memberof PatchedUserDetails + */ + readonly lastName?: string; +} + +/** + * Check if a given object implements the PatchedUserDetails interface. + */ +export function instanceOfPatchedUserDetails(value: object): boolean { + let isInstance = true; + + return isInstance; +} + +export function PatchedUserDetailsFromJSON(json: any): PatchedUserDetails { + return PatchedUserDetailsFromJSONTyped(json, false); +} + +export function PatchedUserDetailsFromJSONTyped(json: any, ignoreDiscriminator: boolean): PatchedUserDetails { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'pk': !exists(json, 'pk') ? undefined : json['pk'], + 'username': !exists(json, 'username') ? undefined : json['username'], + 'email': !exists(json, 'email') ? undefined : json['email'], + 'firstName': !exists(json, 'first_name') ? undefined : json['first_name'], + 'lastName': !exists(json, 'last_name') ? undefined : json['last_name'], + }; +} + +export function PatchedUserDetailsToJSON(value?: PatchedUserDetails | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'username': value.username, + }; +} diff --git a/democrasite-frontend/api/auto/models/RestAuthDetail.ts b/democrasite-frontend/api/auto/models/RestAuthDetail.ts new file mode 100644 index 0000000..230972b --- /dev/null +++ b/democrasite-frontend/api/auto/models/RestAuthDetail.ts @@ -0,0 +1,64 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * + * @export + * @interface RestAuthDetail + */ +export interface RestAuthDetail { + /** + * + * @type {string} + * @memberof RestAuthDetail + */ + readonly detail: string; +} + +/** + * Check if a given object implements the RestAuthDetail interface. + */ +export function instanceOfRestAuthDetail(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "detail" in value; + + return isInstance; +} + +export function RestAuthDetailFromJSON(json: any): RestAuthDetail { + return RestAuthDetailFromJSONTyped(json, false); +} + +export function RestAuthDetailFromJSONTyped(json: any, ignoreDiscriminator: boolean): RestAuthDetail { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'detail': json['detail'], + }; +} + +export function RestAuthDetailToJSON(value?: RestAuthDetail | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + }; +} diff --git a/democrasite-frontend/api/auto/models/SocialLogin.ts b/democrasite-frontend/api/auto/models/SocialLogin.ts new file mode 100644 index 0000000..bf2a093 --- /dev/null +++ b/democrasite-frontend/api/auto/models/SocialLogin.ts @@ -0,0 +1,80 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * + * @export + * @interface SocialLogin + */ +export interface SocialLogin { + /** + * + * @type {string} + * @memberof SocialLogin + */ + accessToken?: string; + /** + * + * @type {string} + * @memberof SocialLogin + */ + code?: string; + /** + * + * @type {string} + * @memberof SocialLogin + */ + idToken?: string; +} + +/** + * Check if a given object implements the SocialLogin interface. + */ +export function instanceOfSocialLogin(value: object): boolean { + let isInstance = true; + + return isInstance; +} + +export function SocialLoginFromJSON(json: any): SocialLogin { + return SocialLoginFromJSONTyped(json, false); +} + +export function SocialLoginFromJSONTyped(json: any, ignoreDiscriminator: boolean): SocialLogin { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'accessToken': !exists(json, 'access_token') ? undefined : json['access_token'], + 'code': !exists(json, 'code') ? undefined : json['code'], + 'idToken': !exists(json, 'id_token') ? undefined : json['id_token'], + }; +} + +export function SocialLoginToJSON(value?: SocialLogin | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'access_token': value.accessToken, + 'code': value.code, + 'id_token': value.idToken, + }; +} diff --git a/democrasite-frontend/api/auto/models/Token.ts b/democrasite-frontend/api/auto/models/Token.ts new file mode 100644 index 0000000..b880ba1 --- /dev/null +++ b/democrasite-frontend/api/auto/models/Token.ts @@ -0,0 +1,65 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * Serializer for Token model. + * @export + * @interface Token + */ +export interface Token { + /** + * + * @type {string} + * @memberof Token + */ + key: string; +} + +/** + * Check if a given object implements the Token interface. + */ +export function instanceOfToken(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "key" in value; + + return isInstance; +} + +export function TokenFromJSON(json: any): Token { + return TokenFromJSONTyped(json, false); +} + +export function TokenFromJSONTyped(json: any, ignoreDiscriminator: boolean): Token { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'key': json['key'], + }; +} + +export function TokenToJSON(value?: Token | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'key': value.key, + }; +} diff --git a/democrasite-frontend/api/auto/models/UserDetails.ts b/democrasite-frontend/api/auto/models/UserDetails.ts new file mode 100644 index 0000000..a98d4bc --- /dev/null +++ b/democrasite-frontend/api/auto/models/UserDetails.ts @@ -0,0 +1,97 @@ +/* tslint:disable */ +/* eslint-disable */ +/** + * Democrasite API + * Documentation of API endpoints of Democrasite + * + * The version of the OpenAPI document: 1.0.0 + * + * + * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). + * https://openapi-generator.tech + * Do not edit the class manually. + */ + +import { exists, mapValues } from '../runtime'; +/** + * User model w/o password + * @export + * @interface UserDetails + */ +export interface UserDetails { + /** + * + * @type {number} + * @memberof UserDetails + */ + readonly pk: number; + /** + * Required. 150 characters or fewer. Letters, digits and @/./+/-/_ only. + * @type {string} + * @memberof UserDetails + */ + username: string; + /** + * + * @type {string} + * @memberof UserDetails + */ + readonly email: string; + /** + * + * @type {string} + * @memberof UserDetails + */ + readonly firstName: string; + /** + * + * @type {string} + * @memberof UserDetails + */ + readonly lastName: string; +} + +/** + * Check if a given object implements the UserDetails interface. + */ +export function instanceOfUserDetails(value: object): boolean { + let isInstance = true; + isInstance = isInstance && "pk" in value; + isInstance = isInstance && "username" in value; + isInstance = isInstance && "email" in value; + isInstance = isInstance && "firstName" in value; + isInstance = isInstance && "lastName" in value; + + return isInstance; +} + +export function UserDetailsFromJSON(json: any): UserDetails { + return UserDetailsFromJSONTyped(json, false); +} + +export function UserDetailsFromJSONTyped(json: any, ignoreDiscriminator: boolean): UserDetails { + if ((json === undefined) || (json === null)) { + return json; + } + return { + + 'pk': json['pk'], + 'username': json['username'], + 'email': json['email'], + 'firstName': json['first_name'], + 'lastName': json['last_name'], + }; +} + +export function UserDetailsToJSON(value?: UserDetails | null): any { + if (value === undefined) { + return undefined; + } + if (value === null) { + return null; + } + return { + + 'username': value.username, + }; +} diff --git a/democrasite-frontend/api/auto/models/index.ts b/democrasite-frontend/api/auto/models/index.ts index 1303ee0..83ec10f 100644 --- a/democrasite-frontend/api/auto/models/index.ts +++ b/democrasite-frontend/api/auto/models/index.ts @@ -1,8 +1,16 @@ /* tslint:disable */ /* eslint-disable */ -export * from './AuthToken'; export * from './Bill'; +export * from './Login'; +export * from './PasswordChange'; +export * from './PasswordReset'; +export * from './PasswordResetConfirm'; export * from './PatchedBill'; export * from './PatchedUser'; +export * from './PatchedUserDetails'; export * from './PullRequest'; +export * from './RestAuthDetail'; +export * from './SocialLogin'; +export * from './Token'; export * from './User'; +export * from './UserDetails'; diff --git a/democrasite-frontend/api/auto/runtime.ts b/democrasite-frontend/api/auto/runtime.ts index 906cea6..3b609e3 100644 --- a/democrasite-frontend/api/auto/runtime.ts +++ b/democrasite-frontend/api/auto/runtime.ts @@ -12,76 +12,87 @@ * Do not edit the class manually. */ - -export const BASE_PATH = "http://localhost".replace(/\/+$/, ""); +export const BASE_PATH = "http://localhost:8000".replace(/\/+$/, ""); export interface ConfigurationParameters { - basePath?: string; // override base path - fetchApi?: FetchAPI; // override for fetch implementation - middleware?: Middleware[]; // middleware to apply before/after fetch requests - queryParamsStringify?: (params: HTTPQuery) => string; // stringify function for query strings - username?: string; // parameter for basic security - password?: string; // parameter for basic security - apiKey?: string | Promise | ((name: string) => string | Promise); // parameter for apiKey security - accessToken?: string | Promise | ((name?: string, scopes?: string[]) => string | Promise); // parameter for oauth2 security - headers?: HTTPHeaders; //header params we want to use on every request - credentials?: RequestCredentials; //value for the credentials param we want to use on each request + basePath?: string; // override base path + fetchApi?: FetchAPI; // override for fetch implementation + middleware?: Middleware[]; // middleware to apply before/after fetch requests + queryParamsStringify?: (params: HTTPQuery) => string; // stringify function for query strings + username?: string; // parameter for basic security + password?: string; // parameter for basic security + apiKey?: + | string + | Promise + | ((name: string) => string | Promise); // parameter for apiKey security + accessToken?: + | string + | Promise + | ((name?: string, scopes?: string[]) => string | Promise); // parameter for oauth2 security + headers?: HTTPHeaders; //header params we want to use on every request + credentials?: RequestCredentials; //value for the credentials param we want to use on each request } export class Configuration { - constructor(private configuration: ConfigurationParameters = {}) {} - - set config(configuration: Configuration) { - this.configuration = configuration; - } - - get basePath(): string { - return this.configuration.basePath != null ? this.configuration.basePath : BASE_PATH; - } - - get fetchApi(): FetchAPI | undefined { - return this.configuration.fetchApi; - } - - get middleware(): Middleware[] { - return this.configuration.middleware || []; - } - - get queryParamsStringify(): (params: HTTPQuery) => string { - return this.configuration.queryParamsStringify || querystring; - } - - get username(): string | undefined { - return this.configuration.username; - } - - get password(): string | undefined { - return this.configuration.password; - } - - get apiKey(): ((name: string) => string | Promise) | undefined { - const apiKey = this.configuration.apiKey; - if (apiKey) { - return typeof apiKey === 'function' ? apiKey : () => apiKey; - } - return undefined; + constructor(private configuration: ConfigurationParameters = {}) {} + + set config(configuration: Configuration) { + this.configuration = configuration; + } + + get basePath(): string { + return this.configuration.basePath != null + ? this.configuration.basePath + : BASE_PATH; + } + + get fetchApi(): FetchAPI | undefined { + return this.configuration.fetchApi; + } + + get middleware(): Middleware[] { + return this.configuration.middleware || []; + } + + get queryParamsStringify(): (params: HTTPQuery) => string { + return this.configuration.queryParamsStringify || querystring; + } + + get username(): string | undefined { + return this.configuration.username; + } + + get password(): string | undefined { + return this.configuration.password; + } + + get apiKey(): ((name: string) => string | Promise) | undefined { + const apiKey = this.configuration.apiKey; + if (apiKey) { + return typeof apiKey === "function" ? apiKey : () => apiKey; } - - get accessToken(): ((name?: string, scopes?: string[]) => string | Promise) | undefined { - const accessToken = this.configuration.accessToken; - if (accessToken) { - return typeof accessToken === 'function' ? accessToken : async () => accessToken; - } - return undefined; + return undefined; + } + + get accessToken(): + | ((name?: string, scopes?: string[]) => string | Promise) + | undefined { + const accessToken = this.configuration.accessToken; + if (accessToken) { + return typeof accessToken === "function" + ? accessToken + : async () => accessToken; } + return undefined; + } - get headers(): HTTPHeaders | undefined { - return this.configuration.headers; - } + get headers(): HTTPHeaders | undefined { + return this.configuration.headers; + } - get credentials(): RequestCredentials | undefined { - return this.configuration.credentials; - } + get credentials(): RequestCredentials | undefined { + return this.configuration.credentials; + } } export const DefaultConfig = new Configuration(); @@ -90,256 +101,333 @@ export const DefaultConfig = new Configuration(); * This is the base class for all generated API classes. */ export class BaseAPI { - - private static readonly jsonRegex = new RegExp('^(:?application\/json|[^;/ \t]+\/[^;/ \t]+[+]json)[ \t]*(:?;.*)?$', 'i'); - private middleware: Middleware[]; - - constructor(protected configuration = DefaultConfig) { - this.middleware = configuration.middleware; + private static readonly jsonRegex = new RegExp( + "^(:?application/json|[^;/ \t]+/[^;/ \t]+[+]json)[ \t]*(:?;.*)?$", + "i" + ); + private middleware: Middleware[]; + + constructor(protected configuration = DefaultConfig) { + this.middleware = configuration.middleware; + } + + withMiddleware(this: T, ...middlewares: Middleware[]) { + const next = this.clone(); + next.middleware = next.middleware.concat(...middlewares); + return next; + } + + withPreMiddleware( + this: T, + ...preMiddlewares: Array + ) { + const middlewares = preMiddlewares.map((pre) => ({ pre })); + return this.withMiddleware(...middlewares); + } + + withPostMiddleware( + this: T, + ...postMiddlewares: Array + ) { + const middlewares = postMiddlewares.map((post) => ({ post })); + return this.withMiddleware(...middlewares); + } + + /** + * Check if the given MIME is a JSON MIME. + * JSON MIME examples: + * application/json + * application/json; charset=UTF8 + * APPLICATION/JSON + * application/vnd.company+json + * @param mime - MIME (Multipurpose Internet Mail Extensions) + * @return True if the given MIME is JSON, false otherwise. + */ + protected isJsonMime(mime: string | null | undefined): boolean { + if (!mime) { + return false; } - - withMiddleware(this: T, ...middlewares: Middleware[]) { - const next = this.clone(); - next.middleware = next.middleware.concat(...middlewares); - return next; + return BaseAPI.jsonRegex.test(mime); + } + + protected async request( + context: RequestOpts, + initOverrides?: RequestInit | InitOverrideFunction + ): Promise { + const { url, init } = await this.createFetchParams(context, initOverrides); + const response = await this.fetchApi(url, init); + if (response && response.status >= 200 && response.status < 300) { + return response; } - - withPreMiddleware(this: T, ...preMiddlewares: Array) { - const middlewares = preMiddlewares.map((pre) => ({ pre })); - return this.withMiddleware(...middlewares); + throw new ResponseError(response, "Response returned an error code"); + } + + private async createFetchParams( + context: RequestOpts, + initOverrides?: RequestInit | InitOverrideFunction + ) { + let url = this.configuration.basePath + context.path; + if ( + context.query !== undefined && + Object.keys(context.query).length !== 0 + ) { + // only add the querystring to the URL if there are query parameters. + // this is done to avoid urls ending with a "?" character which buggy webservers + // do not handle correctly sometimes. + url += "?" + this.configuration.queryParamsStringify(context.query); } - withPostMiddleware(this: T, ...postMiddlewares: Array) { - const middlewares = postMiddlewares.map((post) => ({ post })); - return this.withMiddleware(...middlewares); - } + const headers = Object.assign( + {}, + this.configuration.headers, + context.headers + ); + Object.keys(headers).forEach((key) => + headers[key] === undefined ? delete headers[key] : {} + ); + + const initOverrideFn = + typeof initOverrides === "function" + ? initOverrides + : async () => initOverrides; + + const initParams = { + method: context.method, + headers, + body: context.body, + credentials: this.configuration.credentials, + }; - /** - * Check if the given MIME is a JSON MIME. - * JSON MIME examples: - * application/json - * application/json; charset=UTF8 - * APPLICATION/JSON - * application/vnd.company+json - * @param mime - MIME (Multipurpose Internet Mail Extensions) - * @return True if the given MIME is JSON, false otherwise. - */ - protected isJsonMime(mime: string | null | undefined): boolean { - if (!mime) { - return false; - } - return BaseAPI.jsonRegex.test(mime); - } + const overriddenInit: RequestInit = { + ...initParams, + ...(await initOverrideFn({ + init: initParams, + context, + })), + }; - protected async request(context: RequestOpts, initOverrides?: RequestInit | InitOverrideFunction): Promise { - const { url, init } = await this.createFetchParams(context, initOverrides); - const response = await this.fetchApi(url, init); - if (response && (response.status >= 200 && response.status < 300)) { - return response; - } - throw new ResponseError(response, 'Response returned an error code'); + let body: any; + if ( + isFormData(overriddenInit.body) || + overriddenInit.body instanceof URLSearchParams || + isBlob(overriddenInit.body) + ) { + body = overriddenInit.body; + } else if (this.isJsonMime(headers["Content-Type"])) { + body = JSON.stringify(overriddenInit.body); + } else { + body = overriddenInit.body; } - private async createFetchParams(context: RequestOpts, initOverrides?: RequestInit | InitOverrideFunction) { - let url = this.configuration.basePath + context.path; - if (context.query !== undefined && Object.keys(context.query).length !== 0) { - // only add the querystring to the URL if there are query parameters. - // this is done to avoid urls ending with a "?" character which buggy webservers - // do not handle correctly sometimes. - url += '?' + this.configuration.queryParamsStringify(context.query); - } - - const headers = Object.assign({}, this.configuration.headers, context.headers); - Object.keys(headers).forEach(key => headers[key] === undefined ? delete headers[key] : {}); - - const initOverrideFn = - typeof initOverrides === "function" - ? initOverrides - : async () => initOverrides; - - const initParams = { - method: context.method, - headers, - body: context.body, - credentials: this.configuration.credentials, - }; - - const overriddenInit: RequestInit = { - ...initParams, - ...(await initOverrideFn({ - init: initParams, - context, - })) - }; - - let body: any; - if (isFormData(overriddenInit.body) - || (overriddenInit.body instanceof URLSearchParams) - || isBlob(overriddenInit.body)) { - body = overriddenInit.body; - } else if (this.isJsonMime(headers['Content-Type'])) { - body = JSON.stringify(overriddenInit.body); - } else { - body = overriddenInit.body; - } - - const init: RequestInit = { - ...overriddenInit, - body - }; + const init: RequestInit = { + ...overriddenInit, + body, + }; - return { url, init }; + return { url, init }; + } + + private fetchApi = async (url: string, init: RequestInit) => { + let fetchParams = { url, init }; + for (const middleware of this.middleware) { + if (middleware.pre) { + fetchParams = + (await middleware.pre({ + fetch: this.fetchApi, + ...fetchParams, + })) || fetchParams; + } } - - private fetchApi = async (url: string, init: RequestInit) => { - let fetchParams = { url, init }; - for (const middleware of this.middleware) { - if (middleware.pre) { - fetchParams = await middleware.pre({ - fetch: this.fetchApi, - ...fetchParams, - }) || fetchParams; - } - } - let response: Response | undefined = undefined; - try { - response = await (this.configuration.fetchApi || fetch)(fetchParams.url, fetchParams.init); - } catch (e) { - for (const middleware of this.middleware) { - if (middleware.onError) { - response = await middleware.onError({ - fetch: this.fetchApi, - url: fetchParams.url, - init: fetchParams.init, - error: e, - response: response ? response.clone() : undefined, - }) || response; - } - } - if (response === undefined) { - if (e instanceof Error) { - throw new FetchError(e, 'The request failed and the interceptors did not return an alternative response'); - } else { - throw e; - } - } + let response: Response | undefined = undefined; + try { + response = await (this.configuration.fetchApi || fetch)( + fetchParams.url, + fetchParams.init + ); + } catch (e) { + for (const middleware of this.middleware) { + if (middleware.onError) { + response = + (await middleware.onError({ + fetch: this.fetchApi, + url: fetchParams.url, + init: fetchParams.init, + error: e, + response: response ? response.clone() : undefined, + })) || response; } - for (const middleware of this.middleware) { - if (middleware.post) { - response = await middleware.post({ - fetch: this.fetchApi, - url: fetchParams.url, - init: fetchParams.init, - response: response.clone(), - }) || response; - } + } + if (response === undefined) { + if (e instanceof Error) { + throw new FetchError( + e, + "The request failed and the interceptors did not return an alternative response" + ); + } else { + throw e; } - return response; + } } - - /** - * Create a shallow clone of `this` by constructing a new instance - * and then shallow cloning data members. - */ - private clone(this: T): T { - const constructor = this.constructor as any; - const next = new constructor(this.configuration); - next.middleware = this.middleware.slice(); - return next; + for (const middleware of this.middleware) { + if (middleware.post) { + response = + (await middleware.post({ + fetch: this.fetchApi, + url: fetchParams.url, + init: fetchParams.init, + response: response.clone(), + })) || response; + } } -}; + return response; + }; + + /** + * Create a shallow clone of `this` by constructing a new instance + * and then shallow cloning data members. + */ + private clone(this: T): T { + const constructor = this.constructor as any; + const next = new constructor(this.configuration); + next.middleware = this.middleware.slice(); + return next; + } +} function isBlob(value: any): value is Blob { - return typeof Blob !== 'undefined' && value instanceof Blob; + return typeof Blob !== "undefined" && value instanceof Blob; } function isFormData(value: any): value is FormData { - return typeof FormData !== "undefined" && value instanceof FormData; + return typeof FormData !== "undefined" && value instanceof FormData; } export class ResponseError extends Error { - override name: "ResponseError" = "ResponseError"; - constructor(public response: Response, msg?: string) { - super(msg); - } + override name: "ResponseError" = "ResponseError"; + constructor(public response: Response, msg?: string) { + super(msg); + } } export class FetchError extends Error { - override name: "FetchError" = "FetchError"; - constructor(public cause: Error, msg?: string) { - super(msg); - } + override name: "FetchError" = "FetchError"; + constructor(public cause: Error, msg?: string) { + super(msg); + } } export class RequiredError extends Error { - override name: "RequiredError" = "RequiredError"; - constructor(public field: string, msg?: string) { - super(msg); - } + override name: "RequiredError" = "RequiredError"; + constructor(public field: string, msg?: string) { + super(msg); + } } export const COLLECTION_FORMATS = { - csv: ",", - ssv: " ", - tsv: "\t", - pipes: "|", + csv: ",", + ssv: " ", + tsv: "\t", + pipes: "|", }; -export type FetchAPI = WindowOrWorkerGlobalScope['fetch']; +export type FetchAPI = WindowOrWorkerGlobalScope["fetch"]; export type Json = any; -export type HTTPMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'OPTIONS' | 'HEAD'; +export type HTTPMethod = + | "GET" + | "POST" + | "PUT" + | "PATCH" + | "DELETE" + | "OPTIONS" + | "HEAD"; export type HTTPHeaders = { [key: string]: string }; -export type HTTPQuery = { [key: string]: string | number | null | boolean | Array | Set | HTTPQuery }; +export type HTTPQuery = { + [key: string]: + | string + | number + | null + | boolean + | Array + | Set + | HTTPQuery; +}; export type HTTPBody = Json | FormData | URLSearchParams; -export type HTTPRequestInit = { headers?: HTTPHeaders; method: HTTPMethod; credentials?: RequestCredentials; body?: HTTPBody }; -export type ModelPropertyNaming = 'camelCase' | 'snake_case' | 'PascalCase' | 'original'; +export type HTTPRequestInit = { + headers?: HTTPHeaders; + method: HTTPMethod; + credentials?: RequestCredentials; + body?: HTTPBody; +}; +export type ModelPropertyNaming = + | "camelCase" + | "snake_case" + | "PascalCase" + | "original"; -export type InitOverrideFunction = (requestContext: { init: HTTPRequestInit, context: RequestOpts }) => Promise +export type InitOverrideFunction = (requestContext: { + init: HTTPRequestInit; + context: RequestOpts; +}) => Promise; export interface FetchParams { - url: string; - init: RequestInit; + url: string; + init: RequestInit; } export interface RequestOpts { - path: string; - method: HTTPMethod; - headers: HTTPHeaders; - query?: HTTPQuery; - body?: HTTPBody; + path: string; + method: HTTPMethod; + headers: HTTPHeaders; + query?: HTTPQuery; + body?: HTTPBody; } export function exists(json: any, key: string) { - const value = json[key]; - return value !== null && value !== undefined; + const value = json[key]; + return value !== null && value !== undefined; } -export function querystring(params: HTTPQuery, prefix: string = ''): string { - return Object.keys(params) - .map(key => querystringSingleKey(key, params[key], prefix)) - .filter(part => part.length > 0) - .join('&'); +export function querystring(params: HTTPQuery, prefix: string = ""): string { + return Object.keys(params) + .map((key) => querystringSingleKey(key, params[key], prefix)) + .filter((part) => part.length > 0) + .join("&"); } -function querystringSingleKey(key: string, value: string | number | null | undefined | boolean | Array | Set | HTTPQuery, keyPrefix: string = ''): string { - const fullKey = keyPrefix + (keyPrefix.length ? `[${key}]` : key); - if (value instanceof Array) { - const multiValue = value.map(singleValue => encodeURIComponent(String(singleValue))) - .join(`&${encodeURIComponent(fullKey)}=`); - return `${encodeURIComponent(fullKey)}=${multiValue}`; - } - if (value instanceof Set) { - const valueAsArray = Array.from(value); - return querystringSingleKey(key, valueAsArray, keyPrefix); - } - if (value instanceof Date) { - return `${encodeURIComponent(fullKey)}=${encodeURIComponent(value.toISOString())}`; - } - if (value instanceof Object) { - return querystring(value as HTTPQuery, fullKey); - } - return `${encodeURIComponent(fullKey)}=${encodeURIComponent(String(value))}`; +function querystringSingleKey( + key: string, + value: + | string + | number + | null + | undefined + | boolean + | Array + | Set + | HTTPQuery, + keyPrefix: string = "" +): string { + const fullKey = keyPrefix + (keyPrefix.length ? `[${key}]` : key); + if (value instanceof Array) { + const multiValue = value + .map((singleValue) => encodeURIComponent(String(singleValue))) + .join(`&${encodeURIComponent(fullKey)}=`); + return `${encodeURIComponent(fullKey)}=${multiValue}`; + } + if (value instanceof Set) { + const valueAsArray = Array.from(value); + return querystringSingleKey(key, valueAsArray, keyPrefix); + } + if (value instanceof Date) { + return `${encodeURIComponent(fullKey)}=${encodeURIComponent( + value.toISOString() + )}`; + } + if (value instanceof Object) { + return querystring(value as HTTPQuery, fullKey); + } + return `${encodeURIComponent(fullKey)}=${encodeURIComponent(String(value))}`; } export function mapValues(data: any, fn: (item: any) => any) { @@ -350,82 +438,85 @@ export function mapValues(data: any, fn: (item: any) => any) { } export function canConsumeForm(consumes: Consume[]): boolean { - for (const consume of consumes) { - if ('multipart/form-data' === consume.contentType) { - return true; - } + for (const consume of consumes) { + if ("multipart/form-data" === consume.contentType) { + return true; } - return false; + } + return false; } export interface Consume { - contentType: string; + contentType: string; } export interface RequestContext { - fetch: FetchAPI; - url: string; - init: RequestInit; + fetch: FetchAPI; + url: string; + init: RequestInit; } export interface ResponseContext { - fetch: FetchAPI; - url: string; - init: RequestInit; - response: Response; + fetch: FetchAPI; + url: string; + init: RequestInit; + response: Response; } export interface ErrorContext { - fetch: FetchAPI; - url: string; - init: RequestInit; - error: unknown; - response?: Response; + fetch: FetchAPI; + url: string; + init: RequestInit; + error: unknown; + response?: Response; } export interface Middleware { - pre?(context: RequestContext): Promise; - post?(context: ResponseContext): Promise; - onError?(context: ErrorContext): Promise; + pre?(context: RequestContext): Promise; + post?(context: ResponseContext): Promise; + onError?(context: ErrorContext): Promise; } export interface ApiResponse { - raw: Response; - value(): Promise; + raw: Response; + value(): Promise; } export interface ResponseTransformer { - (json: any): T; + (json: any): T; } export class JSONApiResponse { - constructor(public raw: Response, private transformer: ResponseTransformer = (jsonValue: any) => jsonValue) {} - - async value(): Promise { - return this.transformer(await this.raw.json()); - } + constructor( + public raw: Response, + private transformer: ResponseTransformer = (jsonValue: any) => jsonValue + ) {} + + async value(): Promise { + return this.transformer(await this.raw.json()); + } } export class VoidApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return undefined; - } + async value(): Promise { + return undefined; + } } export class BlobApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return await this.raw.blob(); - }; + async value(): Promise { + return await this.raw.blob(); + } } export class TextApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return await this.raw.text(); - }; + async value(): Promise { + return await this.raw.text(); + } } diff --git a/schema.json b/schema.json index 35cac42..d59d5ef 100644 --- a/schema.json +++ b/schema.json @@ -6,11 +6,762 @@ "description": "Documentation of API endpoints of Democrasite" }, "paths": { + "/api/auth/github/": { + "post": { + "operationId": "auth_github_create", + "description": "class used for social authentications\nexample usage for facebook with access_token\n-------------\nfrom allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter\n\nclass FacebookLogin(SocialLoginView):\n adapter_class = FacebookOAuth2Adapter\n-------------\n\nexample usage for facebook with code\n\n-------------\nfrom allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter\nfrom allauth.socialaccount.providers.oauth2.client import OAuth2Client\n\nclass FacebookLogin(SocialLoginView):\n adapter_class = FacebookOAuth2Adapter\n client_class = OAuth2Client\n callback_url = 'localhost:8000'\n-------------", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/SocialLogin" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/SocialLogin" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/SocialLogin" + } + } + } + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/SocialLogin" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/login/": { + "post": { + "operationId": "auth_login_create", + "description": "Check the credentials and return the REST Token\nif the credentials are valid and authenticated.\nCalls Django Auth login method to register User ID\nin Django session framework\n\nAccept the following POST parameters: username, password\nReturn the REST Framework Token Object's key.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Login" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/Login" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/Login" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Token" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/logout/": { + "post": { + "operationId": "auth_logout_create", + "description": "Calls Django logout method and delete the Token object\nassigned to the current User object.\n\nAccepts/Returns nothing.", + "tags": [ + "auth" + ], + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/password/change/": { + "post": { + "operationId": "auth_password_change_create", + "description": "Calls Django Auth SetPasswordForm save method.\n\nAccepts the following POST parameters: new_password1, new_password2\nReturns the success/fail message.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/password/reset/": { + "post": { + "operationId": "auth_password_reset_create", + "description": "Calls Django Auth PasswordResetForm save method.\n\nAccepts the following POST parameters: email\nReturns the success/fail message.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/password/reset/confirm/": { + "post": { + "operationId": "auth_password_reset_confirm_create", + "description": "Password reset e-mail link is confirmed, therefore\nthis resets the user's password.\n\nAccepts the following POST parameters: token, uid,\n new_password1, new_password2\nReturns the success/fail message.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/auth/user/": { + "get": { + "operationId": "auth_user_retrieve", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "auth" + ], + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + }, + "put": { + "operationId": "auth_user_update", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + }, + "patch": { + "operationId": "auth_user_partial_update", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "auth" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + } + } + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + } + }, + "/api/authlogin/": { + "post": { + "operationId": "authlogin_create", + "description": "Check the credentials and return the REST Token\nif the credentials are valid and authenticated.\nCalls Django Auth login method to register User ID\nin Django session framework\n\nAccept the following POST parameters: username, password\nReturn the REST Framework Token Object's key.", + "tags": [ + "authlogin" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Login" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/Login" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/Login" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Token" + } + } + }, + "description": "" + } + } + } + }, + "/api/authlogout/": { + "post": { + "operationId": "authlogout_create", + "description": "Calls Django logout method and delete the Token object\nassigned to the current User object.\n\nAccepts/Returns nothing.", + "tags": [ + "authlogout" + ], + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/authpassword/change/": { + "post": { + "operationId": "authpassword_change_create", + "description": "Calls Django Auth SetPasswordForm save method.\n\nAccepts the following POST parameters: new_password1, new_password2\nReturns the success/fail message.", + "tags": [ + "authpassword" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordChange" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/authpassword/reset/": { + "post": { + "operationId": "authpassword_reset_create", + "description": "Calls Django Auth PasswordResetForm save method.\n\nAccepts the following POST parameters: email\nReturns the success/fail message.", + "tags": [ + "authpassword" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordReset" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/authpassword/reset/confirm/": { + "post": { + "operationId": "authpassword_reset_confirm_create", + "description": "Password reset e-mail link is confirmed, therefore\nthis resets the user's password.\n\nAccepts the following POST parameters: token, uid,\n new_password1, new_password2\nReturns the success/fail message.", + "tags": [ + "authpassword" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PasswordResetConfirm" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + }, + {} + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/RestAuthDetail" + } + } + }, + "description": "" + } + } + } + }, + "/api/authuser/": { + "get": { + "operationId": "authuser_retrieve", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "authuser" + ], + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + }, + "put": { + "operationId": "authuser_update", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "authuser" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "required": true + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + }, + "patch": { + "operationId": "authuser_partial_update", + "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", + "tags": [ + "authuser" + ], + "requestBody": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + }, + "application/x-www-form-urlencoded": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + }, + "multipart/form-data": { + "schema": { + "$ref": "#/components/schemas/PatchedUserDetails" + } + } + } + }, + "security": [ + { + "cookieAuth": [] + }, + { + "tokenAuth": [] + } + ], + "responses": { + "200": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/UserDetails" + } + } + }, + "description": "" + } + } + } + }, "/api/bills/": { "get": { - "operationId": "api_bills_list", + "operationId": "bills_list", "tags": [ - "api" + "bills" ], "security": [ { @@ -40,7 +791,7 @@ }, "/api/bills/{id}/": { "get": { - "operationId": "api_bills_retrieve", + "operationId": "bills_retrieve", "parameters": [ { "in": "path", @@ -53,7 +804,7 @@ } ], "tags": [ - "api" + "bills" ], "security": [ { @@ -78,7 +829,7 @@ } }, "put": { - "operationId": "api_bills_update", + "operationId": "bills_update", "parameters": [ { "in": "path", @@ -91,7 +842,7 @@ } ], "tags": [ - "api" + "bills" ], "requestBody": { "content": { @@ -135,7 +886,7 @@ } }, "patch": { - "operationId": "api_bills_partial_update", + "operationId": "bills_partial_update", "parameters": [ { "in": "path", @@ -148,7 +899,7 @@ } ], "tags": [ - "api" + "bills" ], "requestBody": { "content": { @@ -193,7 +944,7 @@ }, "/api/schema/": { "get": { - "operationId": "api_schema_retrieve", + "operationId": "schema_retrieve", "description": "OpenApi3 schema for this API. Format can be selected via content negotiation.\n\n- YAML: application/vnd.oai.openapi\n- JSON: application/vnd.oai.openapi+json", "parameters": [ { @@ -316,7 +1067,7 @@ } ], "tags": [ - "api" + "schema" ], "security": [ { @@ -361,9 +1112,9 @@ }, "/api/users/": { "get": { - "operationId": "api_users_list", + "operationId": "users_list", "tags": [ - "api" + "users" ], "security": [ { @@ -393,7 +1144,7 @@ }, "/api/users/{username}/": { "get": { - "operationId": "api_users_retrieve", + "operationId": "users_retrieve", "parameters": [ { "in": "path", @@ -406,7 +1157,7 @@ } ], "tags": [ - "api" + "users" ], "security": [ { @@ -431,7 +1182,7 @@ } }, "put": { - "operationId": "api_users_update", + "operationId": "users_update", "parameters": [ { "in": "path", @@ -444,7 +1195,7 @@ } ], "tags": [ - "api" + "users" ], "requestBody": { "content": { @@ -488,7 +1239,7 @@ } }, "patch": { - "operationId": "api_users_partial_update", + "operationId": "users_partial_update", "parameters": [ { "in": "path", @@ -501,7 +1252,7 @@ } ], "tags": [ - "api" + "users" ], "requestBody": { "content": { @@ -546,9 +1297,9 @@ }, "/api/users/me/": { "get": { - "operationId": "api_users_me_retrieve", + "operationId": "users_me_retrieve", "tags": [ - "api" + "users" ], "security": [ { @@ -572,80 +1323,10 @@ } } } - }, - "/auth-token/": { - "post": { - "operationId": "auth_token_create", - "tags": [ - "auth-token" - ], - "requestBody": { - "content": { - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/AuthToken" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/AuthToken" - } - }, - "application/json": { - "schema": { - "$ref": "#/components/schemas/AuthToken" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - } - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/AuthToken" - } - } - }, - "description": "" - } - } - } } }, "components": { "schemas": { - "AuthToken": { - "type": "object", - "properties": { - "username": { - "type": "string", - "writeOnly": true - }, - "password": { - "type": "string", - "writeOnly": true - }, - "token": { - "type": "string", - "readOnly": true - } - }, - "required": [ - "password", - "token", - "username" - ] - }, "Bill": { "type": "object", "properties": { @@ -715,6 +1396,80 @@ "yes_votes" ] }, + "Login": { + "type": "object", + "properties": { + "username": { + "type": "string" + }, + "email": { + "type": "string", + "format": "email" + }, + "password": { + "type": "string" + } + }, + "required": [ + "password" + ] + }, + "PasswordChange": { + "type": "object", + "properties": { + "new_password1": { + "type": "string", + "maxLength": 128 + }, + "new_password2": { + "type": "string", + "maxLength": 128 + } + }, + "required": [ + "new_password1", + "new_password2" + ] + }, + "PasswordReset": { + "type": "object", + "description": "Serializer for requesting a password reset e-mail.", + "properties": { + "email": { + "type": "string", + "format": "email" + } + }, + "required": [ + "email" + ] + }, + "PasswordResetConfirm": { + "type": "object", + "description": "Serializer for confirming a password reset attempt.", + "properties": { + "new_password1": { + "type": "string", + "maxLength": 128 + }, + "new_password2": { + "type": "string", + "maxLength": 128 + }, + "uid": { + "type": "string" + }, + "token": { + "type": "string" + } + }, + "required": [ + "new_password1", + "new_password2", + "token", + "uid" + ] + }, "PatchedBill": { "type": "object", "properties": { @@ -794,6 +1549,37 @@ } } }, + "PatchedUserDetails": { + "type": "object", + "description": "User model w/o password", + "properties": { + "pk": { + "type": "integer", + "readOnly": true, + "title": "ID" + }, + "username": { + "type": "string", + "description": "Required. 150 characters or fewer. Letters, digits and @/./+/-/_ only.", + "pattern": "^[\\w.@+-]+$", + "maxLength": 150 + }, + "email": { + "type": "string", + "format": "email", + "readOnly": true, + "title": "Email address" + }, + "first_name": { + "type": "string", + "readOnly": true + }, + "last_name": { + "type": "string", + "readOnly": true + } + } + }, "PullRequest": { "type": "object", "properties": { @@ -837,6 +1623,45 @@ "title" ] }, + "RestAuthDetail": { + "type": "object", + "properties": { + "detail": { + "type": "string", + "readOnly": true + } + }, + "required": [ + "detail" + ] + }, + "SocialLogin": { + "type": "object", + "properties": { + "access_token": { + "type": "string" + }, + "code": { + "type": "string" + }, + "id_token": { + "type": "string" + } + } + }, + "Token": { + "type": "object", + "description": "Serializer for Token model.", + "properties": { + "key": { + "type": "string", + "maxLength": 40 + } + }, + "required": [ + "key" + ] + }, "User": { "type": "object", "properties": { @@ -861,6 +1686,44 @@ "url", "username" ] + }, + "UserDetails": { + "type": "object", + "description": "User model w/o password", + "properties": { + "pk": { + "type": "integer", + "readOnly": true, + "title": "ID" + }, + "username": { + "type": "string", + "description": "Required. 150 characters or fewer. Letters, digits and @/./+/-/_ only.", + "pattern": "^[\\w.@+-]+$", + "maxLength": 150 + }, + "email": { + "type": "string", + "format": "email", + "readOnly": true, + "title": "Email address" + }, + "first_name": { + "type": "string", + "readOnly": true + }, + "last_name": { + "type": "string", + "readOnly": true + } + }, + "required": [ + "email", + "first_name", + "last_name", + "pk", + "username" + ] } }, "securitySchemes": { From 244667d9d053e79c6f8c85534cd48b29c95d052c Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 2 Mar 2024 18:59:37 -0500 Subject: [PATCH 03/11] Started using autogenerated api --- democrasite-frontend/app/bills/[id]/page.tsx | 12 ++++++++---- democrasite-frontend/app/page.tsx | 6 ++++-- democrasite-frontend/components/Bill/Bill.tsx | 15 ++++++++------- democrasite-frontend/lib/fetch_bills.tsx | 11 ----------- 4 files changed, 20 insertions(+), 24 deletions(-) delete mode 100644 democrasite-frontend/lib/fetch_bills.tsx diff --git a/democrasite-frontend/app/bills/[id]/page.tsx b/democrasite-frontend/app/bills/[id]/page.tsx index 2914bee..e4eb324 100644 --- a/democrasite-frontend/app/bills/[id]/page.tsx +++ b/democrasite-frontend/app/bills/[id]/page.tsx @@ -1,7 +1,9 @@ import { Container, Center } from "@mantine/core"; import Bill from "@/components/Bill/Bill"; -import fetchBills, { fetchBill } from "@/lib/fetch_bills"; +import { BillsApi } from "@/api/auto"; + +const api = new BillsApi(); export async function generateMetadata({ params, @@ -10,7 +12,9 @@ export async function generateMetadata({ params: { id: number }; searchParams: URLSearchParams; }) { - return { title: `${(await fetchBill(params.id)).name}` }; + return { + title: `${(await api.billsRetrieve({ id: params.id })).name}`, + }; } export default async function BillDetail({ @@ -22,7 +26,7 @@ export default async function BillDetail({
- +
@@ -30,7 +34,7 @@ export default async function BillDetail({ } export async function generateStaticParams() { - const bills = await fetchBills(); + const bills = await api.billsList(); return bills.map((bill: any) => ({ id: bill.id.toString(), diff --git a/democrasite-frontend/app/page.tsx b/democrasite-frontend/app/page.tsx index 306080b..00c2dce 100644 --- a/democrasite-frontend/app/page.tsx +++ b/democrasite-frontend/app/page.tsx @@ -1,10 +1,12 @@ +import { BillsApi } from "@/api/auto"; import BillList from "@/components/BillList/BillList"; -import fetchBills from "@/lib/fetch_bills"; + +const api = new BillsApi(); export default async function Home() { return (
- +
); } diff --git a/democrasite-frontend/components/Bill/Bill.tsx b/democrasite-frontend/components/Bill/Bill.tsx index 7d46f9c..6d7dd37 100644 --- a/democrasite-frontend/components/Bill/Bill.tsx +++ b/democrasite-frontend/components/Bill/Bill.tsx @@ -1,3 +1,4 @@ +import { Bill } from "@/api/auto"; import { Title, Text, @@ -8,13 +9,13 @@ import { Container, } from "@mantine/core"; -export default function Bill({ bill }: any) { +export default function Bill({ bill }: { bill: Bill }) { return ( - Bill {bill.id}: {bill.name} (PR #{bill.pull_request.number}) + Bill {bill.id}: {bill.name} (PR #{bill.pullRequest.number}) {bill.constitutional && Constitutional Amendment} @@ -26,20 +27,20 @@ export default function Bill({ bill }: any) { {bill.description} - + - +{bill.pull_request.additions} + +{bill.pullRequest.additions} - -{bill.pull_request.deletions} + -{bill.pullRequest.deletions} - Yes: {bill.yes_votes.length} + Yes: {bill.yesVotes.length} - No: {bill.no_votes.length} + No: {bill.noVotes.length} diff --git a/democrasite-frontend/lib/fetch_bills.tsx b/democrasite-frontend/lib/fetch_bills.tsx deleted file mode 100644 index 0c11f1b..0000000 --- a/democrasite-frontend/lib/fetch_bills.tsx +++ /dev/null @@ -1,11 +0,0 @@ -export default function fetchBills() { - return fetch(`${process.env.BASE_API_URL}/bills/`, { - next: { revalidate: 60 }, // revalidate every minute for testing - }).then((response) => response.json()); -} - -export function fetchBill(id: number) { - return fetch(`${process.env.BASE_API_URL}/bills/${id}`, { - cache: "no-store", // no caching for testing (probably want to cache info but not vote data) - }).then((response) => response.json()); -} From 542cf11a28c89dcf182380a22931708e907c3637 Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sun, 3 Mar 2024 00:55:10 -0500 Subject: [PATCH 04/11] Moved auto api --- democrasite-frontend/app/bills/[id]/page.tsx | 4 +-- democrasite-frontend/components/Bill/Bill.tsx | 4 +-- .../components/BillList/BillList.tsx | 28 ++----------------- democrasite-frontend/components/index.ts | 3 ++ .../auto/.openapi-generator-ignore | 0 .../auto/.openapi-generator/FILES | 0 .../auto/.openapi-generator/VERSION | 0 .../{api => lib}/auto/apis/AuthApi.ts | 0 .../{api => lib}/auto/apis/AuthloginApi.ts | 0 .../{api => lib}/auto/apis/AuthlogoutApi.ts | 0 .../{api => lib}/auto/apis/AuthpasswordApi.ts | 0 .../{api => lib}/auto/apis/AuthuserApi.ts | 0 .../{api => lib}/auto/apis/BillsApi.ts | 0 .../{api => lib}/auto/apis/SchemaApi.ts | 0 .../{api => lib}/auto/apis/UsersApi.ts | 0 .../{api => lib}/auto/apis/index.ts | 0 .../{api => lib}/auto/index.ts | 0 .../{api => lib}/auto/models/AuthToken.ts | 0 .../{api => lib}/auto/models/Bill.ts | 0 .../{api => lib}/auto/models/Login.ts | 0 .../auto/models/PasswordChange.ts | 0 .../{api => lib}/auto/models/PasswordReset.ts | 0 .../auto/models/PasswordResetConfirm.ts | 0 .../{api => lib}/auto/models/PatchedBill.ts | 0 .../{api => lib}/auto/models/PatchedUser.ts | 0 .../auto/models/PatchedUserDetails.ts | 0 .../{api => lib}/auto/models/PullRequest.ts | 0 .../auto/models/RestAuthDetail.ts | 0 .../{api => lib}/auto/models/SocialLogin.ts | 0 .../{api => lib}/auto/models/Token.ts | 0 .../{api => lib}/auto/models/User.ts | 0 .../{api => lib}/auto/models/UserDetails.ts | 0 .../{api => lib}/auto/models/index.ts | 0 .../{api => lib}/auto/runtime.ts | 0 34 files changed, 9 insertions(+), 30 deletions(-) create mode 100644 democrasite-frontend/components/index.ts rename democrasite-frontend/{api => lib}/auto/.openapi-generator-ignore (100%) rename democrasite-frontend/{api => lib}/auto/.openapi-generator/FILES (100%) rename democrasite-frontend/{api => lib}/auto/.openapi-generator/VERSION (100%) rename democrasite-frontend/{api => lib}/auto/apis/AuthApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/AuthloginApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/AuthlogoutApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/AuthpasswordApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/AuthuserApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/BillsApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/SchemaApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/UsersApi.ts (100%) rename democrasite-frontend/{api => lib}/auto/apis/index.ts (100%) rename democrasite-frontend/{api => lib}/auto/index.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/AuthToken.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/Bill.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/Login.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PasswordChange.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PasswordReset.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PasswordResetConfirm.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PatchedBill.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PatchedUser.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PatchedUserDetails.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/PullRequest.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/RestAuthDetail.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/SocialLogin.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/Token.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/User.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/UserDetails.ts (100%) rename democrasite-frontend/{api => lib}/auto/models/index.ts (100%) rename democrasite-frontend/{api => lib}/auto/runtime.ts (100%) diff --git a/democrasite-frontend/app/bills/[id]/page.tsx b/democrasite-frontend/app/bills/[id]/page.tsx index e4eb324..ce499b3 100644 --- a/democrasite-frontend/app/bills/[id]/page.tsx +++ b/democrasite-frontend/app/bills/[id]/page.tsx @@ -1,7 +1,7 @@ import { Container, Center } from "@mantine/core"; -import Bill from "@/components/Bill/Bill"; -import { BillsApi } from "@/api/auto"; +import { Bill } from "@/components"; +import { BillsApi } from "@/lib/auto"; const api = new BillsApi(); diff --git a/democrasite-frontend/components/Bill/Bill.tsx b/democrasite-frontend/components/Bill/Bill.tsx index 6d7dd37..1edd5ce 100644 --- a/democrasite-frontend/components/Bill/Bill.tsx +++ b/democrasite-frontend/components/Bill/Bill.tsx @@ -1,4 +1,4 @@ -import { Bill } from "@/api/auto"; +import { Bill } from "@/lib/auto"; import { Title, Text, @@ -9,7 +9,7 @@ import { Container, } from "@mantine/core"; -export default function Bill({ bill }: { bill: Bill }) { +export function Bill({ bill }: { bill: Bill }) { return ( diff --git a/democrasite-frontend/components/BillList/BillList.tsx b/democrasite-frontend/components/BillList/BillList.tsx index 4eafde8..2f6f46f 100644 --- a/democrasite-frontend/components/BillList/BillList.tsx +++ b/democrasite-frontend/components/BillList/BillList.tsx @@ -1,31 +1,7 @@ import { Card, Grid, GridCol } from "@mantine/core"; -import Bill from "../../components/Bill/Bill"; +import { Bill } from "@/components"; -const bills = [ - { - name: "test", - description: "This is a test", - time_created: "2024-02-19T00:05:35.164799-06:00", - author: "http://127.0.0.1:8000/api/users/matthew/", - pull_request: "http://127.0.0.1:8000/api/pull-requests/-1/", - yes_votes: [], - no_votes: ["http://127.0.0.1:8000/api/users/mfosterw/"], - url: "http://127.0.0.1:8000/api/bills/1/", - }, - { - name: "hi", - description: - "This bill has an extremely long-winded description. In fact, the description is so long that it will have to be cut off when being displayed. That makes it a pretty long description in my opinion.", - time_created: "2024-02-19T00:05:35.164799-06:00", - author: "http://127.0.0.1:8000/api/users/matthew/", - pull_request: "http://127.0.0.1:8000/api/pull-requests/-2/", - yes_votes: ["http://127.0.0.1:8000/api/users/mfosterw/"], - no_votes: [], - url: "http://127.0.0.1:8000/api/bills/18/", - }, -]; - -export default function BillList(props: any) { +export function BillList(props: any) { const cards = props.bill_list.map((bill: any) => ( diff --git a/democrasite-frontend/components/index.ts b/democrasite-frontend/components/index.ts new file mode 100644 index 0000000..cb096a0 --- /dev/null +++ b/democrasite-frontend/components/index.ts @@ -0,0 +1,3 @@ +export * from "./Bill/Bill"; +export * from "./BillList/BillList"; +export * from "./SignInButton/SignInButton"; diff --git a/democrasite-frontend/api/auto/.openapi-generator-ignore b/democrasite-frontend/lib/auto/.openapi-generator-ignore similarity index 100% rename from democrasite-frontend/api/auto/.openapi-generator-ignore rename to democrasite-frontend/lib/auto/.openapi-generator-ignore diff --git a/democrasite-frontend/api/auto/.openapi-generator/FILES b/democrasite-frontend/lib/auto/.openapi-generator/FILES similarity index 100% rename from democrasite-frontend/api/auto/.openapi-generator/FILES rename to democrasite-frontend/lib/auto/.openapi-generator/FILES diff --git a/democrasite-frontend/api/auto/.openapi-generator/VERSION b/democrasite-frontend/lib/auto/.openapi-generator/VERSION similarity index 100% rename from democrasite-frontend/api/auto/.openapi-generator/VERSION rename to democrasite-frontend/lib/auto/.openapi-generator/VERSION diff --git a/democrasite-frontend/api/auto/apis/AuthApi.ts b/democrasite-frontend/lib/auto/apis/AuthApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/AuthApi.ts rename to democrasite-frontend/lib/auto/apis/AuthApi.ts diff --git a/democrasite-frontend/api/auto/apis/AuthloginApi.ts b/democrasite-frontend/lib/auto/apis/AuthloginApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/AuthloginApi.ts rename to democrasite-frontend/lib/auto/apis/AuthloginApi.ts diff --git a/democrasite-frontend/api/auto/apis/AuthlogoutApi.ts b/democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/AuthlogoutApi.ts rename to democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts diff --git a/democrasite-frontend/api/auto/apis/AuthpasswordApi.ts b/democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/AuthpasswordApi.ts rename to democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts diff --git a/democrasite-frontend/api/auto/apis/AuthuserApi.ts b/democrasite-frontend/lib/auto/apis/AuthuserApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/AuthuserApi.ts rename to democrasite-frontend/lib/auto/apis/AuthuserApi.ts diff --git a/democrasite-frontend/api/auto/apis/BillsApi.ts b/democrasite-frontend/lib/auto/apis/BillsApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/BillsApi.ts rename to democrasite-frontend/lib/auto/apis/BillsApi.ts diff --git a/democrasite-frontend/api/auto/apis/SchemaApi.ts b/democrasite-frontend/lib/auto/apis/SchemaApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/SchemaApi.ts rename to democrasite-frontend/lib/auto/apis/SchemaApi.ts diff --git a/democrasite-frontend/api/auto/apis/UsersApi.ts b/democrasite-frontend/lib/auto/apis/UsersApi.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/UsersApi.ts rename to democrasite-frontend/lib/auto/apis/UsersApi.ts diff --git a/democrasite-frontend/api/auto/apis/index.ts b/democrasite-frontend/lib/auto/apis/index.ts similarity index 100% rename from democrasite-frontend/api/auto/apis/index.ts rename to democrasite-frontend/lib/auto/apis/index.ts diff --git a/democrasite-frontend/api/auto/index.ts b/democrasite-frontend/lib/auto/index.ts similarity index 100% rename from democrasite-frontend/api/auto/index.ts rename to democrasite-frontend/lib/auto/index.ts diff --git a/democrasite-frontend/api/auto/models/AuthToken.ts b/democrasite-frontend/lib/auto/models/AuthToken.ts similarity index 100% rename from democrasite-frontend/api/auto/models/AuthToken.ts rename to democrasite-frontend/lib/auto/models/AuthToken.ts diff --git a/democrasite-frontend/api/auto/models/Bill.ts b/democrasite-frontend/lib/auto/models/Bill.ts similarity index 100% rename from democrasite-frontend/api/auto/models/Bill.ts rename to democrasite-frontend/lib/auto/models/Bill.ts diff --git a/democrasite-frontend/api/auto/models/Login.ts b/democrasite-frontend/lib/auto/models/Login.ts similarity index 100% rename from democrasite-frontend/api/auto/models/Login.ts rename to democrasite-frontend/lib/auto/models/Login.ts diff --git a/democrasite-frontend/api/auto/models/PasswordChange.ts b/democrasite-frontend/lib/auto/models/PasswordChange.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PasswordChange.ts rename to democrasite-frontend/lib/auto/models/PasswordChange.ts diff --git a/democrasite-frontend/api/auto/models/PasswordReset.ts b/democrasite-frontend/lib/auto/models/PasswordReset.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PasswordReset.ts rename to democrasite-frontend/lib/auto/models/PasswordReset.ts diff --git a/democrasite-frontend/api/auto/models/PasswordResetConfirm.ts b/democrasite-frontend/lib/auto/models/PasswordResetConfirm.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PasswordResetConfirm.ts rename to democrasite-frontend/lib/auto/models/PasswordResetConfirm.ts diff --git a/democrasite-frontend/api/auto/models/PatchedBill.ts b/democrasite-frontend/lib/auto/models/PatchedBill.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PatchedBill.ts rename to democrasite-frontend/lib/auto/models/PatchedBill.ts diff --git a/democrasite-frontend/api/auto/models/PatchedUser.ts b/democrasite-frontend/lib/auto/models/PatchedUser.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PatchedUser.ts rename to democrasite-frontend/lib/auto/models/PatchedUser.ts diff --git a/democrasite-frontend/api/auto/models/PatchedUserDetails.ts b/democrasite-frontend/lib/auto/models/PatchedUserDetails.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PatchedUserDetails.ts rename to democrasite-frontend/lib/auto/models/PatchedUserDetails.ts diff --git a/democrasite-frontend/api/auto/models/PullRequest.ts b/democrasite-frontend/lib/auto/models/PullRequest.ts similarity index 100% rename from democrasite-frontend/api/auto/models/PullRequest.ts rename to democrasite-frontend/lib/auto/models/PullRequest.ts diff --git a/democrasite-frontend/api/auto/models/RestAuthDetail.ts b/democrasite-frontend/lib/auto/models/RestAuthDetail.ts similarity index 100% rename from democrasite-frontend/api/auto/models/RestAuthDetail.ts rename to democrasite-frontend/lib/auto/models/RestAuthDetail.ts diff --git a/democrasite-frontend/api/auto/models/SocialLogin.ts b/democrasite-frontend/lib/auto/models/SocialLogin.ts similarity index 100% rename from democrasite-frontend/api/auto/models/SocialLogin.ts rename to democrasite-frontend/lib/auto/models/SocialLogin.ts diff --git a/democrasite-frontend/api/auto/models/Token.ts b/democrasite-frontend/lib/auto/models/Token.ts similarity index 100% rename from democrasite-frontend/api/auto/models/Token.ts rename to democrasite-frontend/lib/auto/models/Token.ts diff --git a/democrasite-frontend/api/auto/models/User.ts b/democrasite-frontend/lib/auto/models/User.ts similarity index 100% rename from democrasite-frontend/api/auto/models/User.ts rename to democrasite-frontend/lib/auto/models/User.ts diff --git a/democrasite-frontend/api/auto/models/UserDetails.ts b/democrasite-frontend/lib/auto/models/UserDetails.ts similarity index 100% rename from democrasite-frontend/api/auto/models/UserDetails.ts rename to democrasite-frontend/lib/auto/models/UserDetails.ts diff --git a/democrasite-frontend/api/auto/models/index.ts b/democrasite-frontend/lib/auto/models/index.ts similarity index 100% rename from democrasite-frontend/api/auto/models/index.ts rename to democrasite-frontend/lib/auto/models/index.ts diff --git a/democrasite-frontend/api/auto/runtime.ts b/democrasite-frontend/lib/auto/runtime.ts similarity index 100% rename from democrasite-frontend/api/auto/runtime.ts rename to democrasite-frontend/lib/auto/runtime.ts From 163fe291cdb3a0e9604e6954150a1e05eb880489 Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Mon, 4 Mar 2024 22:57:07 -0500 Subject: [PATCH 05/11] Remove duplicate auth routes --- config/urls.py | 2 - schema.json | 351 ------------------------------------------------- 2 files changed, 353 deletions(-) diff --git a/config/urls.py b/config/urls.py index 1e0f22c..dc63f01 100644 --- a/config/urls.py +++ b/config/urls.py @@ -35,8 +35,6 @@ urlpatterns += [ # API base url path("api/", include("config.api_router")), - # DRF auth token - path("api/auth", include("dj_rest_auth.urls")), path("api/schema/", SpectacularAPIView.as_view(), name="api-schema"), path( "api/docs/", diff --git a/schema.json b/schema.json index d59d5ef..d08ee1f 100644 --- a/schema.json +++ b/schema.json @@ -406,357 +406,6 @@ } } }, - "/api/authlogin/": { - "post": { - "operationId": "authlogin_create", - "description": "Check the credentials and return the REST Token\nif the credentials are valid and authenticated.\nCalls Django Auth login method to register User ID\nin Django session framework\n\nAccept the following POST parameters: username, password\nReturn the REST Framework Token Object's key.", - "tags": [ - "authlogin" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Login" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/Login" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/Login" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - }, - {} - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/Token" - } - } - }, - "description": "" - } - } - } - }, - "/api/authlogout/": { - "post": { - "operationId": "authlogout_create", - "description": "Calls Django logout method and delete the Token object\nassigned to the current User object.\n\nAccepts/Returns nothing.", - "tags": [ - "authlogout" - ], - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - }, - {} - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/RestAuthDetail" - } - } - }, - "description": "" - } - } - } - }, - "/api/authpassword/change/": { - "post": { - "operationId": "authpassword_change_create", - "description": "Calls Django Auth SetPasswordForm save method.\n\nAccepts the following POST parameters: new_password1, new_password2\nReturns the success/fail message.", - "tags": [ - "authpassword" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PasswordChange" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/PasswordChange" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/PasswordChange" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - } - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/RestAuthDetail" - } - } - }, - "description": "" - } - } - } - }, - "/api/authpassword/reset/": { - "post": { - "operationId": "authpassword_reset_create", - "description": "Calls Django Auth PasswordResetForm save method.\n\nAccepts the following POST parameters: email\nReturns the success/fail message.", - "tags": [ - "authpassword" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PasswordReset" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/PasswordReset" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/PasswordReset" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - }, - {} - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/RestAuthDetail" - } - } - }, - "description": "" - } - } - } - }, - "/api/authpassword/reset/confirm/": { - "post": { - "operationId": "authpassword_reset_confirm_create", - "description": "Password reset e-mail link is confirmed, therefore\nthis resets the user's password.\n\nAccepts the following POST parameters: token, uid,\n new_password1, new_password2\nReturns the success/fail message.", - "tags": [ - "authpassword" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PasswordResetConfirm" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/PasswordResetConfirm" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/PasswordResetConfirm" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - }, - {} - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/RestAuthDetail" - } - } - }, - "description": "" - } - } - } - }, - "/api/authuser/": { - "get": { - "operationId": "authuser_retrieve", - "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", - "tags": [ - "authuser" - ], - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - } - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - } - }, - "description": "" - } - } - }, - "put": { - "operationId": "authuser_update", - "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", - "tags": [ - "authuser" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - } - }, - "required": true - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - } - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - } - }, - "description": "" - } - } - }, - "patch": { - "operationId": "authuser_partial_update", - "description": "Reads and updates UserModel fields\nAccepts GET, PUT, PATCH methods.\n\nDefault accepted fields: username, first_name, last_name\nDefault display fields: pk, username, email, first_name, last_name\nRead-only fields: pk, email\n\nReturns UserModel fields.", - "tags": [ - "authuser" - ], - "requestBody": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/PatchedUserDetails" - } - }, - "application/x-www-form-urlencoded": { - "schema": { - "$ref": "#/components/schemas/PatchedUserDetails" - } - }, - "multipart/form-data": { - "schema": { - "$ref": "#/components/schemas/PatchedUserDetails" - } - } - } - }, - "security": [ - { - "cookieAuth": [] - }, - { - "tokenAuth": [] - } - ], - "responses": { - "200": { - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/UserDetails" - } - } - }, - "description": "" - } - } - } - }, "/api/bills/": { "get": { "operationId": "bills_list", From 44b7df630b3f933f700f3785e2149ec95999b90b Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Mon, 4 Mar 2024 23:05:31 -0500 Subject: [PATCH 06/11] Fixed schema for github login --- .../lib/auto/.openapi-generator-ignore | 1 - .../lib/auto/.openapi-generator/FILES | 5 +- democrasite-frontend/lib/auto/apis/AuthApi.ts | 12 +- .../lib/auto/apis/AuthloginApi.ts | 74 -------- .../lib/auto/apis/AuthlogoutApi.ts | 60 ------- .../lib/auto/apis/AuthpasswordApi.ts | 162 ------------------ .../lib/auto/apis/AuthuserApi.ts | 141 --------------- democrasite-frontend/lib/auto/apis/index.ts | 4 - .../lib/auto/models/AuthToken.ts | 82 --------- democrasite/users/api/views.py | 10 ++ schema.json | 5 +- 11 files changed, 21 insertions(+), 535 deletions(-) delete mode 100644 democrasite-frontend/lib/auto/apis/AuthloginApi.ts delete mode 100644 democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts delete mode 100644 democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts delete mode 100644 democrasite-frontend/lib/auto/apis/AuthuserApi.ts delete mode 100644 democrasite-frontend/lib/auto/models/AuthToken.ts diff --git a/democrasite-frontend/lib/auto/.openapi-generator-ignore b/democrasite-frontend/lib/auto/.openapi-generator-ignore index 8904a39..7484ee5 100644 --- a/democrasite-frontend/lib/auto/.openapi-generator-ignore +++ b/democrasite-frontend/lib/auto/.openapi-generator-ignore @@ -3,7 +3,6 @@ # Use this file to prevent files from being overwritten by the generator. # The patterns follow closely to .gitignore or .dockerignore. -# Note that this should be avoided when possible to keep the API client in sync with the API definition. # As an example, the C# client generator defines ApiClient.cs. # You can make changes and tell OpenAPI Generator to ignore just this file by uncommenting the following line: diff --git a/democrasite-frontend/lib/auto/.openapi-generator/FILES b/democrasite-frontend/lib/auto/.openapi-generator/FILES index 9b2a9d7..872f7bc 100644 --- a/democrasite-frontend/lib/auto/.openapi-generator/FILES +++ b/democrasite-frontend/lib/auto/.openapi-generator/FILES @@ -1,8 +1,5 @@ +.openapi-generator-ignore apis/AuthApi.ts -apis/AuthloginApi.ts -apis/AuthlogoutApi.ts -apis/AuthpasswordApi.ts -apis/AuthuserApi.ts apis/BillsApi.ts apis/SchemaApi.ts apis/UsersApi.ts diff --git a/democrasite-frontend/lib/auto/apis/AuthApi.ts b/democrasite-frontend/lib/auto/apis/AuthApi.ts index bf2ff40..7877fa4 100644 --- a/democrasite-frontend/lib/auto/apis/AuthApi.ts +++ b/democrasite-frontend/lib/auto/apis/AuthApi.ts @@ -80,9 +80,10 @@ export interface AuthUserUpdateRequest { export class AuthApi extends runtime.BaseAPI { /** - * class used for social authentications example usage for facebook with access_token ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter ------------- example usage for facebook with code ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter from allauth.socialaccount.providers.oauth2.client import OAuth2Client class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter client_class = OAuth2Client callback_url = \'localhost:8000\' ------------- + * Login with GitHub using OAuth2 + * Login with GitHub */ - async authGithubCreateRaw(requestParameters: AuthGithubCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { + async authGithubCreateRaw(requestParameters: AuthGithubCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { const queryParameters: any = {}; const headerParameters: runtime.HTTPHeaders = {}; @@ -101,13 +102,14 @@ export class AuthApi extends runtime.BaseAPI { body: SocialLoginToJSON(requestParameters.socialLogin), }, initOverrides); - return new runtime.JSONApiResponse(response, (jsonValue) => SocialLoginFromJSON(jsonValue)); + return new runtime.JSONApiResponse(response, (jsonValue) => TokenFromJSON(jsonValue)); } /** - * class used for social authentications example usage for facebook with access_token ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter ------------- example usage for facebook with code ------------- from allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter from allauth.socialaccount.providers.oauth2.client import OAuth2Client class FacebookLogin(SocialLoginView): adapter_class = FacebookOAuth2Adapter client_class = OAuth2Client callback_url = \'localhost:8000\' ------------- + * Login with GitHub using OAuth2 + * Login with GitHub */ - async authGithubCreate(requestParameters: AuthGithubCreateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { + async authGithubCreate(requestParameters: AuthGithubCreateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { const response = await this.authGithubCreateRaw(requestParameters, initOverrides); return await response.value(); } diff --git a/democrasite-frontend/lib/auto/apis/AuthloginApi.ts b/democrasite-frontend/lib/auto/apis/AuthloginApi.ts deleted file mode 100644 index dbaf9aa..0000000 --- a/democrasite-frontend/lib/auto/apis/AuthloginApi.ts +++ /dev/null @@ -1,74 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - Login, - Token, -} from '../models/index'; -import { - LoginFromJSON, - LoginToJSON, - TokenFromJSON, - TokenToJSON, -} from '../models/index'; - -export interface AuthloginCreateRequest { - login: Login; -} - -/** - * - */ -export class AuthloginApi extends runtime.BaseAPI { - - /** - * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. - */ - async authloginCreateRaw(requestParameters: AuthloginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.login === null || requestParameters.login === undefined) { - throw new runtime.RequiredError('login','Required parameter requestParameters.login was null or undefined when calling authloginCreate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authlogin/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - body: LoginToJSON(requestParameters.login), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => TokenFromJSON(jsonValue)); - } - - /** - * Check the credentials and return the REST Token if the credentials are valid and authenticated. Calls Django Auth login method to register User ID in Django session framework Accept the following POST parameters: username, password Return the REST Framework Token Object\'s key. - */ - async authloginCreate(requestParameters: AuthloginCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authloginCreateRaw(requestParameters, initOverrides); - return await response.value(); - } - -} diff --git a/democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts b/democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts deleted file mode 100644 index f229ad8..0000000 --- a/democrasite-frontend/lib/auto/apis/AuthlogoutApi.ts +++ /dev/null @@ -1,60 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - RestAuthDetail, -} from '../models/index'; -import { - RestAuthDetailFromJSON, - RestAuthDetailToJSON, -} from '../models/index'; - -/** - * - */ -export class AuthlogoutApi extends runtime.BaseAPI { - - /** - * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. - */ - async authlogoutCreateRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authlogout/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); - } - - /** - * Calls Django logout method and delete the Token object assigned to the current User object. Accepts/Returns nothing. - */ - async authlogoutCreate(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authlogoutCreateRaw(initOverrides); - return await response.value(); - } - -} diff --git a/democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts b/democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts deleted file mode 100644 index 03131c0..0000000 --- a/democrasite-frontend/lib/auto/apis/AuthpasswordApi.ts +++ /dev/null @@ -1,162 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - PasswordChange, - PasswordReset, - PasswordResetConfirm, - RestAuthDetail, -} from '../models/index'; -import { - PasswordChangeFromJSON, - PasswordChangeToJSON, - PasswordResetFromJSON, - PasswordResetToJSON, - PasswordResetConfirmFromJSON, - PasswordResetConfirmToJSON, - RestAuthDetailFromJSON, - RestAuthDetailToJSON, -} from '../models/index'; - -export interface AuthpasswordChangeCreateRequest { - passwordChange: PasswordChange; -} - -export interface AuthpasswordResetConfirmCreateRequest { - passwordResetConfirm: PasswordResetConfirm; -} - -export interface AuthpasswordResetCreateRequest { - passwordReset: PasswordReset; -} - -/** - * - */ -export class AuthpasswordApi extends runtime.BaseAPI { - - /** - * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. - */ - async authpasswordChangeCreateRaw(requestParameters: AuthpasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.passwordChange === null || requestParameters.passwordChange === undefined) { - throw new runtime.RequiredError('passwordChange','Required parameter requestParameters.passwordChange was null or undefined when calling authpasswordChangeCreate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authpassword/change/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - body: PasswordChangeToJSON(requestParameters.passwordChange), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); - } - - /** - * Calls Django Auth SetPasswordForm save method. Accepts the following POST parameters: new_password1, new_password2 Returns the success/fail message. - */ - async authpasswordChangeCreate(requestParameters: AuthpasswordChangeCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authpasswordChangeCreateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. - */ - async authpasswordResetConfirmCreateRaw(requestParameters: AuthpasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.passwordResetConfirm === null || requestParameters.passwordResetConfirm === undefined) { - throw new runtime.RequiredError('passwordResetConfirm','Required parameter requestParameters.passwordResetConfirm was null or undefined when calling authpasswordResetConfirmCreate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authpassword/reset/confirm/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - body: PasswordResetConfirmToJSON(requestParameters.passwordResetConfirm), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); - } - - /** - * Password reset e-mail link is confirmed, therefore this resets the user\'s password. Accepts the following POST parameters: token, uid, new_password1, new_password2 Returns the success/fail message. - */ - async authpasswordResetConfirmCreate(requestParameters: AuthpasswordResetConfirmCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authpasswordResetConfirmCreateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. - */ - async authpasswordResetCreateRaw(requestParameters: AuthpasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.passwordReset === null || requestParameters.passwordReset === undefined) { - throw new runtime.RequiredError('passwordReset','Required parameter requestParameters.passwordReset was null or undefined when calling authpasswordResetCreate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authpassword/reset/`, - method: 'POST', - headers: headerParameters, - query: queryParameters, - body: PasswordResetToJSON(requestParameters.passwordReset), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => RestAuthDetailFromJSON(jsonValue)); - } - - /** - * Calls Django Auth PasswordResetForm save method. Accepts the following POST parameters: email Returns the success/fail message. - */ - async authpasswordResetCreate(requestParameters: AuthpasswordResetCreateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authpasswordResetCreateRaw(requestParameters, initOverrides); - return await response.value(); - } - -} diff --git a/democrasite-frontend/lib/auto/apis/AuthuserApi.ts b/democrasite-frontend/lib/auto/apis/AuthuserApi.ts deleted file mode 100644 index c2c2728..0000000 --- a/democrasite-frontend/lib/auto/apis/AuthuserApi.ts +++ /dev/null @@ -1,141 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - - -import * as runtime from '../runtime'; -import type { - PatchedUserDetails, - UserDetails, -} from '../models/index'; -import { - PatchedUserDetailsFromJSON, - PatchedUserDetailsToJSON, - UserDetailsFromJSON, - UserDetailsToJSON, -} from '../models/index'; - -export interface AuthuserPartialUpdateRequest { - patchedUserDetails?: PatchedUserDetails; -} - -export interface AuthuserUpdateRequest { - userDetails: UserDetails; -} - -/** - * - */ -export class AuthuserApi extends runtime.BaseAPI { - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserPartialUpdateRaw(requestParameters: AuthuserPartialUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authuser/`, - method: 'PATCH', - headers: headerParameters, - query: queryParameters, - body: PatchedUserDetailsToJSON(requestParameters.patchedUserDetails), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); - } - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserPartialUpdate(requestParameters: AuthuserPartialUpdateRequest = {}, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authuserPartialUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserRetrieveRaw(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authuser/`, - method: 'GET', - headers: headerParameters, - query: queryParameters, - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); - } - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserRetrieve(initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authuserRetrieveRaw(initOverrides); - return await response.value(); - } - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserUpdateRaw(requestParameters: AuthuserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise> { - if (requestParameters.userDetails === null || requestParameters.userDetails === undefined) { - throw new runtime.RequiredError('userDetails','Required parameter requestParameters.userDetails was null or undefined when calling authuserUpdate.'); - } - - const queryParameters: any = {}; - - const headerParameters: runtime.HTTPHeaders = {}; - - headerParameters['Content-Type'] = 'application/json'; - - if (this.configuration && this.configuration.apiKey) { - headerParameters["Authorization"] = await this.configuration.apiKey("Authorization"); // tokenAuth authentication - } - - const response = await this.request({ - path: `/api/authuser/`, - method: 'PUT', - headers: headerParameters, - query: queryParameters, - body: UserDetailsToJSON(requestParameters.userDetails), - }, initOverrides); - - return new runtime.JSONApiResponse(response, (jsonValue) => UserDetailsFromJSON(jsonValue)); - } - - /** - * Reads and updates UserModel fields Accepts GET, PUT, PATCH methods. Default accepted fields: username, first_name, last_name Default display fields: pk, username, email, first_name, last_name Read-only fields: pk, email Returns UserModel fields. - */ - async authuserUpdate(requestParameters: AuthuserUpdateRequest, initOverrides?: RequestInit | runtime.InitOverrideFunction): Promise { - const response = await this.authuserUpdateRaw(requestParameters, initOverrides); - return await response.value(); - } - -} diff --git a/democrasite-frontend/lib/auto/apis/index.ts b/democrasite-frontend/lib/auto/apis/index.ts index 5d1cdf3..86a7402 100644 --- a/democrasite-frontend/lib/auto/apis/index.ts +++ b/democrasite-frontend/lib/auto/apis/index.ts @@ -1,10 +1,6 @@ /* tslint:disable */ /* eslint-disable */ export * from './AuthApi'; -export * from './AuthloginApi'; -export * from './AuthlogoutApi'; -export * from './AuthpasswordApi'; -export * from './AuthuserApi'; export * from './BillsApi'; export * from './SchemaApi'; export * from './UsersApi'; diff --git a/democrasite-frontend/lib/auto/models/AuthToken.ts b/democrasite-frontend/lib/auto/models/AuthToken.ts deleted file mode 100644 index b4db4be..0000000 --- a/democrasite-frontend/lib/auto/models/AuthToken.ts +++ /dev/null @@ -1,82 +0,0 @@ -/* tslint:disable */ -/* eslint-disable */ -/** - * Democrasite API - * Documentation of API endpoints of Democrasite - * - * The version of the OpenAPI document: 1.0.0 - * - * - * NOTE: This class is auto generated by OpenAPI Generator (https://openapi-generator.tech). - * https://openapi-generator.tech - * Do not edit the class manually. - */ - -import { exists, mapValues } from '../runtime'; -/** - * - * @export - * @interface AuthToken - */ -export interface AuthToken { - /** - * - * @type {string} - * @memberof AuthToken - */ - username: string; - /** - * - * @type {string} - * @memberof AuthToken - */ - password: string; - /** - * - * @type {string} - * @memberof AuthToken - */ - readonly token: string; -} - -/** - * Check if a given object implements the AuthToken interface. - */ -export function instanceOfAuthToken(value: object): boolean { - let isInstance = true; - isInstance = isInstance && "username" in value; - isInstance = isInstance && "password" in value; - isInstance = isInstance && "token" in value; - - return isInstance; -} - -export function AuthTokenFromJSON(json: any): AuthToken { - return AuthTokenFromJSONTyped(json, false); -} - -export function AuthTokenFromJSONTyped(json: any, ignoreDiscriminator: boolean): AuthToken { - if ((json === undefined) || (json === null)) { - return json; - } - return { - - 'username': json['username'], - 'password': json['password'], - 'token': json['token'], - }; -} - -export function AuthTokenToJSON(value?: AuthToken | null): any { - if (value === undefined) { - return undefined; - } - if (value === null) { - return null; - } - return { - - 'username': value.username, - 'password': value.password, - }; -} diff --git a/democrasite/users/api/views.py b/democrasite/users/api/views.py index 72790de..2baddb6 100644 --- a/democrasite/users/api/views.py +++ b/democrasite/users/api/views.py @@ -1,7 +1,10 @@ from allauth.socialaccount.providers.github.views import GitHubOAuth2Adapter from allauth.socialaccount.providers.oauth2.client import OAuth2Client from dj_rest_auth.registration.views import SocialLoginView +from dj_rest_auth.serializers import TokenSerializer from django.urls import reverse +from drf_spectacular.utils import extend_schema +from drf_spectacular.utils import extend_schema_view from rest_framework import status from rest_framework.decorators import action from rest_framework.mixins import ListModelMixin @@ -33,6 +36,13 @@ def me(self, request): # dj-rest-auth views +@extend_schema_view( + post=extend_schema( + summary="Login with GitHub", + description="Login with GitHub using OAuth2", + responses=TokenSerializer, + ) +) class GitHubLogin(SocialLoginView): adapter_class = GitHubOAuth2Adapter callback_url = reverse("github_callback") diff --git a/schema.json b/schema.json index d08ee1f..f720ad6 100644 --- a/schema.json +++ b/schema.json @@ -9,7 +9,8 @@ "/api/auth/github/": { "post": { "operationId": "auth_github_create", - "description": "class used for social authentications\nexample usage for facebook with access_token\n-------------\nfrom allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter\n\nclass FacebookLogin(SocialLoginView):\n adapter_class = FacebookOAuth2Adapter\n-------------\n\nexample usage for facebook with code\n\n-------------\nfrom allauth.socialaccount.providers.facebook.views import FacebookOAuth2Adapter\nfrom allauth.socialaccount.providers.oauth2.client import OAuth2Client\n\nclass FacebookLogin(SocialLoginView):\n adapter_class = FacebookOAuth2Adapter\n client_class = OAuth2Client\n callback_url = 'localhost:8000'\n-------------", + "description": "Login with GitHub using OAuth2", + "summary": "Login with GitHub", "tags": [ "auth" ], @@ -46,7 +47,7 @@ "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/SocialLogin" + "$ref": "#/components/schemas/Token" } } }, From 60b0a537da315013892517df2da667792437b7fc Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 9 Mar 2024 21:06:53 -0500 Subject: [PATCH 07/11] Improved user_supports field on bills --- democrasite/webiscite/api/serializers.py | 15 +++++++++ democrasite/webiscite/api/views.py | 41 +++--------------------- democrasite/webiscite/models.py | 18 +++++++++++ 3 files changed, 38 insertions(+), 36 deletions(-) diff --git a/democrasite/webiscite/api/serializers.py b/democrasite/webiscite/api/serializers.py index e2f3528..9e16d67 100644 --- a/democrasite/webiscite/api/serializers.py +++ b/democrasite/webiscite/api/serializers.py @@ -2,6 +2,7 @@ from rest_framework.serializers import CharField from rest_framework.serializers import ModelSerializer +from rest_framework.serializers import SerializerMethodField from rest_framework.serializers import SlugRelatedField from democrasite.users.api.serializers import UserSerializer @@ -37,6 +38,7 @@ class BillSerializer(ModelSerializer): no_votes: "SlugRelatedField[User]" = SlugRelatedField( many=True, read_only=True, slug_field="username" ) + user_supports = SerializerMethodField(required=False) class Meta: model = Bill @@ -49,4 +51,17 @@ class Meta: "created", "yes_votes", "no_votes", + "user_supports", ] + + def get_user_supports(self, bill: Bill) -> bool | None: + """Return whether the user supports the bill. If the user is not authenticated + or has not voted on this bill, return None. + + Args: + bill: The bill to check + + Returns: + Whether the user supports the bill, or None if not applicable""" + user: User = self.context["user"] + return bill.user_supports(user) if user.is_authenticated else None diff --git a/democrasite/webiscite/api/views.py b/democrasite/webiscite/api/views.py index cb6d139..f679646 100644 --- a/democrasite/webiscite/api/views.py +++ b/democrasite/webiscite/api/views.py @@ -1,12 +1,8 @@ -import contextlib from typing import Any -from django.db.models import Prefetch from rest_framework.mixins import ListModelMixin from rest_framework.mixins import RetrieveModelMixin from rest_framework.mixins import UpdateModelMixin -from rest_framework.request import Request -from rest_framework.response import Response from rest_framework.viewsets import GenericViewSet from democrasite.webiscite.models import Bill @@ -18,36 +14,9 @@ class BillViewSet(RetrieveModelMixin, ListModelMixin, UpdateModelMixin, GenericV serializer_class = BillSerializer queryset = Bill.objects.select_related("author", "pull_request") - def retrieve(self, request: Request, *args: Any, **kwargs: Any) -> Response: - response = super().retrieve(request, *args, **kwargs) + def get_serializer_context(self) -> dict[str, Any]: + context = super().get_serializer_context() + context["user"] = self.request.user + return context - if request.user.is_authenticated: - bill: Bill = self.get_object() - with contextlib.suppress(bill.vote_set.model.DoesNotExist): - response.data["user_supports"] = bill.vote_set.get( - user=request.user - ).support - - return response - - def list(self, request: Request, *args: Any, **kwargs: Any) -> Response: - response = super().list(request, *args, **kwargs) - - if request.user.is_authenticated: - user_votes_prefetch = Prefetch( - "vote_set", queryset=request.user.vote_set.all(), to_attr="user_votes" - ) - - bill_ids = [bill["id"] for bill in response.data] - # Need a new database call in order to prefetch the user's votes - bills = Bill.objects.filter(id__in=bill_ids).prefetch_related( - user_votes_prefetch - ) - for bill, bill_dict in zip(bills, response.data, strict=True): - vote_query = bill.user_votes # type: ignore [attr-defined] - - # Guaranteed to be at most one element, avoids calling database again - for vote in vote_query: - bill_dict["user_supports"] = vote.support - - return response + # TODO: Prefetch bill list votes diff --git a/democrasite/webiscite/models.py b/democrasite/webiscite/models.py index cb9f964..d9abc81 100644 --- a/democrasite/webiscite/models.py +++ b/democrasite/webiscite/models.py @@ -201,6 +201,24 @@ def vote(self, user: User, *, support: bool) -> None: # Just waiting for new version to be released self.votes.add(user, through_defaults={"support": support}) # type: ignore[call-arg] + def user_supports(self, user: User) -> bool | None: + """ + Returns whether the given user supports, opposes, or has not voted on this bill + + Args: + user: The user to check + + Returns: + True if the user supports the bill, False if they oppose it, and None if + they have not voted + """ + try: + vote: Vote = self.vote_set.get(user=user) + except Vote.DoesNotExist: + return None + else: + return vote.support + @classmethod def create_from_pr(cls, pr: dict[str, Any]) -> tuple[PullRequest, Self | None]: """Create a :class:`~democrasite.webiscite.models.PullRequest` and, if the From 0772cb569af49773f1b7b6f3e987dc70e9d6db6d Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 9 Mar 2024 21:12:27 -0500 Subject: [PATCH 08/11] Updated frontend api --- config/settings/base.py | 1 + .../lib/auto/.openapi-generator/FILES | 1 - democrasite-frontend/lib/auto/models/Bill.ts | 15 + .../lib/auto/models/PatchedBill.ts | 14 + democrasite-frontend/lib/auto/runtime.ts | 695 ++++++++---------- schema.json | 13 + 6 files changed, 345 insertions(+), 394 deletions(-) diff --git a/config/settings/base.py b/config/settings/base.py index c5f15a1..41bce8a 100644 --- a/config/settings/base.py +++ b/config/settings/base.py @@ -96,6 +96,7 @@ "corsheaders", "drf_spectacular", "dj_rest_auth", + "dj_rest_auth.registration", # Machina (forum) dependencies: "mptt", "haystack", diff --git a/democrasite-frontend/lib/auto/.openapi-generator/FILES b/democrasite-frontend/lib/auto/.openapi-generator/FILES index 872f7bc..71805f7 100644 --- a/democrasite-frontend/lib/auto/.openapi-generator/FILES +++ b/democrasite-frontend/lib/auto/.openapi-generator/FILES @@ -1,4 +1,3 @@ -.openapi-generator-ignore apis/AuthApi.ts apis/BillsApi.ts apis/SchemaApi.ts diff --git a/democrasite-frontend/lib/auto/models/Bill.ts b/democrasite-frontend/lib/auto/models/Bill.ts index da11661..bb25fa2 100644 --- a/democrasite-frontend/lib/auto/models/Bill.ts +++ b/democrasite-frontend/lib/auto/models/Bill.ts @@ -68,6 +68,19 @@ export interface Bill { * @memberof Bill */ readonly noVotes: Array; + /** + * Return whether the user supports the bill. If the user is not authenticated + * or has not voted on this bill, return None. + * + * Args: + * bill: The bill to check + * + * Returns: + * Whether the user supports the bill, or None if not applicable + * @type {boolean} + * @memberof Bill + */ + readonly userSupports: boolean | null; /** * * @type {Date} @@ -111,6 +124,7 @@ export function instanceOfBill(value: object): boolean { isInstance = isInstance && "status" in value; isInstance = isInstance && "yesVotes" in value; isInstance = isInstance && "noVotes" in value; + isInstance = isInstance && "userSupports" in value; isInstance = isInstance && "created" in value; isInstance = isInstance && "name" in value; isInstance = isInstance && "constitutional" in value; @@ -134,6 +148,7 @@ export function BillFromJSONTyped(json: any, ignoreDiscriminator: boolean): Bill 'status': json['status'], 'yesVotes': json['yes_votes'], 'noVotes': json['no_votes'], + 'userSupports': json['user_supports'], 'created': (new Date(json['created'])), 'statusChanged': !exists(json, 'status_changed') ? undefined : (new Date(json['status_changed'])), 'name': json['name'], diff --git a/democrasite-frontend/lib/auto/models/PatchedBill.ts b/democrasite-frontend/lib/auto/models/PatchedBill.ts index 07daa2c..6e5338c 100644 --- a/democrasite-frontend/lib/auto/models/PatchedBill.ts +++ b/democrasite-frontend/lib/auto/models/PatchedBill.ts @@ -68,6 +68,19 @@ export interface PatchedBill { * @memberof PatchedBill */ readonly noVotes?: Array; + /** + * Return whether the user supports the bill. If the user is not authenticated + * or has not voted on this bill, return None. + * + * Args: + * bill: The bill to check + * + * Returns: + * Whether the user supports the bill, or None if not applicable + * @type {boolean} + * @memberof PatchedBill + */ + readonly userSupports?: boolean | null; /** * * @type {Date} @@ -125,6 +138,7 @@ export function PatchedBillFromJSONTyped(json: any, ignoreDiscriminator: boolean 'status': !exists(json, 'status') ? undefined : json['status'], 'yesVotes': !exists(json, 'yes_votes') ? undefined : json['yes_votes'], 'noVotes': !exists(json, 'no_votes') ? undefined : json['no_votes'], + 'userSupports': !exists(json, 'user_supports') ? undefined : json['user_supports'], 'created': !exists(json, 'created') ? undefined : (new Date(json['created'])), 'statusChanged': !exists(json, 'status_changed') ? undefined : (new Date(json['status_changed'])), 'name': !exists(json, 'name') ? undefined : json['name'], diff --git a/democrasite-frontend/lib/auto/runtime.ts b/democrasite-frontend/lib/auto/runtime.ts index 3b609e3..906cea6 100644 --- a/democrasite-frontend/lib/auto/runtime.ts +++ b/democrasite-frontend/lib/auto/runtime.ts @@ -12,87 +12,76 @@ * Do not edit the class manually. */ -export const BASE_PATH = "http://localhost:8000".replace(/\/+$/, ""); + +export const BASE_PATH = "http://localhost".replace(/\/+$/, ""); export interface ConfigurationParameters { - basePath?: string; // override base path - fetchApi?: FetchAPI; // override for fetch implementation - middleware?: Middleware[]; // middleware to apply before/after fetch requests - queryParamsStringify?: (params: HTTPQuery) => string; // stringify function for query strings - username?: string; // parameter for basic security - password?: string; // parameter for basic security - apiKey?: - | string - | Promise - | ((name: string) => string | Promise); // parameter for apiKey security - accessToken?: - | string - | Promise - | ((name?: string, scopes?: string[]) => string | Promise); // parameter for oauth2 security - headers?: HTTPHeaders; //header params we want to use on every request - credentials?: RequestCredentials; //value for the credentials param we want to use on each request + basePath?: string; // override base path + fetchApi?: FetchAPI; // override for fetch implementation + middleware?: Middleware[]; // middleware to apply before/after fetch requests + queryParamsStringify?: (params: HTTPQuery) => string; // stringify function for query strings + username?: string; // parameter for basic security + password?: string; // parameter for basic security + apiKey?: string | Promise | ((name: string) => string | Promise); // parameter for apiKey security + accessToken?: string | Promise | ((name?: string, scopes?: string[]) => string | Promise); // parameter for oauth2 security + headers?: HTTPHeaders; //header params we want to use on every request + credentials?: RequestCredentials; //value for the credentials param we want to use on each request } export class Configuration { - constructor(private configuration: ConfigurationParameters = {}) {} - - set config(configuration: Configuration) { - this.configuration = configuration; - } - - get basePath(): string { - return this.configuration.basePath != null - ? this.configuration.basePath - : BASE_PATH; - } - - get fetchApi(): FetchAPI | undefined { - return this.configuration.fetchApi; - } - - get middleware(): Middleware[] { - return this.configuration.middleware || []; - } - - get queryParamsStringify(): (params: HTTPQuery) => string { - return this.configuration.queryParamsStringify || querystring; - } - - get username(): string | undefined { - return this.configuration.username; - } - - get password(): string | undefined { - return this.configuration.password; - } - - get apiKey(): ((name: string) => string | Promise) | undefined { - const apiKey = this.configuration.apiKey; - if (apiKey) { - return typeof apiKey === "function" ? apiKey : () => apiKey; + constructor(private configuration: ConfigurationParameters = {}) {} + + set config(configuration: Configuration) { + this.configuration = configuration; + } + + get basePath(): string { + return this.configuration.basePath != null ? this.configuration.basePath : BASE_PATH; + } + + get fetchApi(): FetchAPI | undefined { + return this.configuration.fetchApi; + } + + get middleware(): Middleware[] { + return this.configuration.middleware || []; + } + + get queryParamsStringify(): (params: HTTPQuery) => string { + return this.configuration.queryParamsStringify || querystring; + } + + get username(): string | undefined { + return this.configuration.username; + } + + get password(): string | undefined { + return this.configuration.password; + } + + get apiKey(): ((name: string) => string | Promise) | undefined { + const apiKey = this.configuration.apiKey; + if (apiKey) { + return typeof apiKey === 'function' ? apiKey : () => apiKey; + } + return undefined; } - return undefined; - } - - get accessToken(): - | ((name?: string, scopes?: string[]) => string | Promise) - | undefined { - const accessToken = this.configuration.accessToken; - if (accessToken) { - return typeof accessToken === "function" - ? accessToken - : async () => accessToken; + + get accessToken(): ((name?: string, scopes?: string[]) => string | Promise) | undefined { + const accessToken = this.configuration.accessToken; + if (accessToken) { + return typeof accessToken === 'function' ? accessToken : async () => accessToken; + } + return undefined; } - return undefined; - } - get headers(): HTTPHeaders | undefined { - return this.configuration.headers; - } + get headers(): HTTPHeaders | undefined { + return this.configuration.headers; + } - get credentials(): RequestCredentials | undefined { - return this.configuration.credentials; - } + get credentials(): RequestCredentials | undefined { + return this.configuration.credentials; + } } export const DefaultConfig = new Configuration(); @@ -101,333 +90,256 @@ export const DefaultConfig = new Configuration(); * This is the base class for all generated API classes. */ export class BaseAPI { - private static readonly jsonRegex = new RegExp( - "^(:?application/json|[^;/ \t]+/[^;/ \t]+[+]json)[ \t]*(:?;.*)?$", - "i" - ); - private middleware: Middleware[]; - - constructor(protected configuration = DefaultConfig) { - this.middleware = configuration.middleware; - } - - withMiddleware(this: T, ...middlewares: Middleware[]) { - const next = this.clone(); - next.middleware = next.middleware.concat(...middlewares); - return next; - } - - withPreMiddleware( - this: T, - ...preMiddlewares: Array - ) { - const middlewares = preMiddlewares.map((pre) => ({ pre })); - return this.withMiddleware(...middlewares); - } - - withPostMiddleware( - this: T, - ...postMiddlewares: Array - ) { - const middlewares = postMiddlewares.map((post) => ({ post })); - return this.withMiddleware(...middlewares); - } - - /** - * Check if the given MIME is a JSON MIME. - * JSON MIME examples: - * application/json - * application/json; charset=UTF8 - * APPLICATION/JSON - * application/vnd.company+json - * @param mime - MIME (Multipurpose Internet Mail Extensions) - * @return True if the given MIME is JSON, false otherwise. - */ - protected isJsonMime(mime: string | null | undefined): boolean { - if (!mime) { - return false; + + private static readonly jsonRegex = new RegExp('^(:?application\/json|[^;/ \t]+\/[^;/ \t]+[+]json)[ \t]*(:?;.*)?$', 'i'); + private middleware: Middleware[]; + + constructor(protected configuration = DefaultConfig) { + this.middleware = configuration.middleware; } - return BaseAPI.jsonRegex.test(mime); - } - - protected async request( - context: RequestOpts, - initOverrides?: RequestInit | InitOverrideFunction - ): Promise { - const { url, init } = await this.createFetchParams(context, initOverrides); - const response = await this.fetchApi(url, init); - if (response && response.status >= 200 && response.status < 300) { - return response; + + withMiddleware(this: T, ...middlewares: Middleware[]) { + const next = this.clone(); + next.middleware = next.middleware.concat(...middlewares); + return next; } - throw new ResponseError(response, "Response returned an error code"); - } - - private async createFetchParams( - context: RequestOpts, - initOverrides?: RequestInit | InitOverrideFunction - ) { - let url = this.configuration.basePath + context.path; - if ( - context.query !== undefined && - Object.keys(context.query).length !== 0 - ) { - // only add the querystring to the URL if there are query parameters. - // this is done to avoid urls ending with a "?" character which buggy webservers - // do not handle correctly sometimes. - url += "?" + this.configuration.queryParamsStringify(context.query); + + withPreMiddleware(this: T, ...preMiddlewares: Array) { + const middlewares = preMiddlewares.map((pre) => ({ pre })); + return this.withMiddleware(...middlewares); } - const headers = Object.assign( - {}, - this.configuration.headers, - context.headers - ); - Object.keys(headers).forEach((key) => - headers[key] === undefined ? delete headers[key] : {} - ); - - const initOverrideFn = - typeof initOverrides === "function" - ? initOverrides - : async () => initOverrides; - - const initParams = { - method: context.method, - headers, - body: context.body, - credentials: this.configuration.credentials, - }; + withPostMiddleware(this: T, ...postMiddlewares: Array) { + const middlewares = postMiddlewares.map((post) => ({ post })); + return this.withMiddleware(...middlewares); + } - const overriddenInit: RequestInit = { - ...initParams, - ...(await initOverrideFn({ - init: initParams, - context, - })), - }; + /** + * Check if the given MIME is a JSON MIME. + * JSON MIME examples: + * application/json + * application/json; charset=UTF8 + * APPLICATION/JSON + * application/vnd.company+json + * @param mime - MIME (Multipurpose Internet Mail Extensions) + * @return True if the given MIME is JSON, false otherwise. + */ + protected isJsonMime(mime: string | null | undefined): boolean { + if (!mime) { + return false; + } + return BaseAPI.jsonRegex.test(mime); + } - let body: any; - if ( - isFormData(overriddenInit.body) || - overriddenInit.body instanceof URLSearchParams || - isBlob(overriddenInit.body) - ) { - body = overriddenInit.body; - } else if (this.isJsonMime(headers["Content-Type"])) { - body = JSON.stringify(overriddenInit.body); - } else { - body = overriddenInit.body; + protected async request(context: RequestOpts, initOverrides?: RequestInit | InitOverrideFunction): Promise { + const { url, init } = await this.createFetchParams(context, initOverrides); + const response = await this.fetchApi(url, init); + if (response && (response.status >= 200 && response.status < 300)) { + return response; + } + throw new ResponseError(response, 'Response returned an error code'); } - const init: RequestInit = { - ...overriddenInit, - body, - }; + private async createFetchParams(context: RequestOpts, initOverrides?: RequestInit | InitOverrideFunction) { + let url = this.configuration.basePath + context.path; + if (context.query !== undefined && Object.keys(context.query).length !== 0) { + // only add the querystring to the URL if there are query parameters. + // this is done to avoid urls ending with a "?" character which buggy webservers + // do not handle correctly sometimes. + url += '?' + this.configuration.queryParamsStringify(context.query); + } + + const headers = Object.assign({}, this.configuration.headers, context.headers); + Object.keys(headers).forEach(key => headers[key] === undefined ? delete headers[key] : {}); + + const initOverrideFn = + typeof initOverrides === "function" + ? initOverrides + : async () => initOverrides; + + const initParams = { + method: context.method, + headers, + body: context.body, + credentials: this.configuration.credentials, + }; + + const overriddenInit: RequestInit = { + ...initParams, + ...(await initOverrideFn({ + init: initParams, + context, + })) + }; + + let body: any; + if (isFormData(overriddenInit.body) + || (overriddenInit.body instanceof URLSearchParams) + || isBlob(overriddenInit.body)) { + body = overriddenInit.body; + } else if (this.isJsonMime(headers['Content-Type'])) { + body = JSON.stringify(overriddenInit.body); + } else { + body = overriddenInit.body; + } + + const init: RequestInit = { + ...overriddenInit, + body + }; - return { url, init }; - } - - private fetchApi = async (url: string, init: RequestInit) => { - let fetchParams = { url, init }; - for (const middleware of this.middleware) { - if (middleware.pre) { - fetchParams = - (await middleware.pre({ - fetch: this.fetchApi, - ...fetchParams, - })) || fetchParams; - } + return { url, init }; } - let response: Response | undefined = undefined; - try { - response = await (this.configuration.fetchApi || fetch)( - fetchParams.url, - fetchParams.init - ); - } catch (e) { - for (const middleware of this.middleware) { - if (middleware.onError) { - response = - (await middleware.onError({ - fetch: this.fetchApi, - url: fetchParams.url, - init: fetchParams.init, - error: e, - response: response ? response.clone() : undefined, - })) || response; + + private fetchApi = async (url: string, init: RequestInit) => { + let fetchParams = { url, init }; + for (const middleware of this.middleware) { + if (middleware.pre) { + fetchParams = await middleware.pre({ + fetch: this.fetchApi, + ...fetchParams, + }) || fetchParams; + } } - } - if (response === undefined) { - if (e instanceof Error) { - throw new FetchError( - e, - "The request failed and the interceptors did not return an alternative response" - ); - } else { - throw e; + let response: Response | undefined = undefined; + try { + response = await (this.configuration.fetchApi || fetch)(fetchParams.url, fetchParams.init); + } catch (e) { + for (const middleware of this.middleware) { + if (middleware.onError) { + response = await middleware.onError({ + fetch: this.fetchApi, + url: fetchParams.url, + init: fetchParams.init, + error: e, + response: response ? response.clone() : undefined, + }) || response; + } + } + if (response === undefined) { + if (e instanceof Error) { + throw new FetchError(e, 'The request failed and the interceptors did not return an alternative response'); + } else { + throw e; + } + } } - } + for (const middleware of this.middleware) { + if (middleware.post) { + response = await middleware.post({ + fetch: this.fetchApi, + url: fetchParams.url, + init: fetchParams.init, + response: response.clone(), + }) || response; + } + } + return response; } - for (const middleware of this.middleware) { - if (middleware.post) { - response = - (await middleware.post({ - fetch: this.fetchApi, - url: fetchParams.url, - init: fetchParams.init, - response: response.clone(), - })) || response; - } + + /** + * Create a shallow clone of `this` by constructing a new instance + * and then shallow cloning data members. + */ + private clone(this: T): T { + const constructor = this.constructor as any; + const next = new constructor(this.configuration); + next.middleware = this.middleware.slice(); + return next; } - return response; - }; - - /** - * Create a shallow clone of `this` by constructing a new instance - * and then shallow cloning data members. - */ - private clone(this: T): T { - const constructor = this.constructor as any; - const next = new constructor(this.configuration); - next.middleware = this.middleware.slice(); - return next; - } -} +}; function isBlob(value: any): value is Blob { - return typeof Blob !== "undefined" && value instanceof Blob; + return typeof Blob !== 'undefined' && value instanceof Blob; } function isFormData(value: any): value is FormData { - return typeof FormData !== "undefined" && value instanceof FormData; + return typeof FormData !== "undefined" && value instanceof FormData; } export class ResponseError extends Error { - override name: "ResponseError" = "ResponseError"; - constructor(public response: Response, msg?: string) { - super(msg); - } + override name: "ResponseError" = "ResponseError"; + constructor(public response: Response, msg?: string) { + super(msg); + } } export class FetchError extends Error { - override name: "FetchError" = "FetchError"; - constructor(public cause: Error, msg?: string) { - super(msg); - } + override name: "FetchError" = "FetchError"; + constructor(public cause: Error, msg?: string) { + super(msg); + } } export class RequiredError extends Error { - override name: "RequiredError" = "RequiredError"; - constructor(public field: string, msg?: string) { - super(msg); - } + override name: "RequiredError" = "RequiredError"; + constructor(public field: string, msg?: string) { + super(msg); + } } export const COLLECTION_FORMATS = { - csv: ",", - ssv: " ", - tsv: "\t", - pipes: "|", + csv: ",", + ssv: " ", + tsv: "\t", + pipes: "|", }; -export type FetchAPI = WindowOrWorkerGlobalScope["fetch"]; +export type FetchAPI = WindowOrWorkerGlobalScope['fetch']; export type Json = any; -export type HTTPMethod = - | "GET" - | "POST" - | "PUT" - | "PATCH" - | "DELETE" - | "OPTIONS" - | "HEAD"; +export type HTTPMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'OPTIONS' | 'HEAD'; export type HTTPHeaders = { [key: string]: string }; -export type HTTPQuery = { - [key: string]: - | string - | number - | null - | boolean - | Array - | Set - | HTTPQuery; -}; +export type HTTPQuery = { [key: string]: string | number | null | boolean | Array | Set | HTTPQuery }; export type HTTPBody = Json | FormData | URLSearchParams; -export type HTTPRequestInit = { - headers?: HTTPHeaders; - method: HTTPMethod; - credentials?: RequestCredentials; - body?: HTTPBody; -}; -export type ModelPropertyNaming = - | "camelCase" - | "snake_case" - | "PascalCase" - | "original"; +export type HTTPRequestInit = { headers?: HTTPHeaders; method: HTTPMethod; credentials?: RequestCredentials; body?: HTTPBody }; +export type ModelPropertyNaming = 'camelCase' | 'snake_case' | 'PascalCase' | 'original'; -export type InitOverrideFunction = (requestContext: { - init: HTTPRequestInit; - context: RequestOpts; -}) => Promise; +export type InitOverrideFunction = (requestContext: { init: HTTPRequestInit, context: RequestOpts }) => Promise export interface FetchParams { - url: string; - init: RequestInit; + url: string; + init: RequestInit; } export interface RequestOpts { - path: string; - method: HTTPMethod; - headers: HTTPHeaders; - query?: HTTPQuery; - body?: HTTPBody; + path: string; + method: HTTPMethod; + headers: HTTPHeaders; + query?: HTTPQuery; + body?: HTTPBody; } export function exists(json: any, key: string) { - const value = json[key]; - return value !== null && value !== undefined; + const value = json[key]; + return value !== null && value !== undefined; } -export function querystring(params: HTTPQuery, prefix: string = ""): string { - return Object.keys(params) - .map((key) => querystringSingleKey(key, params[key], prefix)) - .filter((part) => part.length > 0) - .join("&"); +export function querystring(params: HTTPQuery, prefix: string = ''): string { + return Object.keys(params) + .map(key => querystringSingleKey(key, params[key], prefix)) + .filter(part => part.length > 0) + .join('&'); } -function querystringSingleKey( - key: string, - value: - | string - | number - | null - | undefined - | boolean - | Array - | Set - | HTTPQuery, - keyPrefix: string = "" -): string { - const fullKey = keyPrefix + (keyPrefix.length ? `[${key}]` : key); - if (value instanceof Array) { - const multiValue = value - .map((singleValue) => encodeURIComponent(String(singleValue))) - .join(`&${encodeURIComponent(fullKey)}=`); - return `${encodeURIComponent(fullKey)}=${multiValue}`; - } - if (value instanceof Set) { - const valueAsArray = Array.from(value); - return querystringSingleKey(key, valueAsArray, keyPrefix); - } - if (value instanceof Date) { - return `${encodeURIComponent(fullKey)}=${encodeURIComponent( - value.toISOString() - )}`; - } - if (value instanceof Object) { - return querystring(value as HTTPQuery, fullKey); - } - return `${encodeURIComponent(fullKey)}=${encodeURIComponent(String(value))}`; +function querystringSingleKey(key: string, value: string | number | null | undefined | boolean | Array | Set | HTTPQuery, keyPrefix: string = ''): string { + const fullKey = keyPrefix + (keyPrefix.length ? `[${key}]` : key); + if (value instanceof Array) { + const multiValue = value.map(singleValue => encodeURIComponent(String(singleValue))) + .join(`&${encodeURIComponent(fullKey)}=`); + return `${encodeURIComponent(fullKey)}=${multiValue}`; + } + if (value instanceof Set) { + const valueAsArray = Array.from(value); + return querystringSingleKey(key, valueAsArray, keyPrefix); + } + if (value instanceof Date) { + return `${encodeURIComponent(fullKey)}=${encodeURIComponent(value.toISOString())}`; + } + if (value instanceof Object) { + return querystring(value as HTTPQuery, fullKey); + } + return `${encodeURIComponent(fullKey)}=${encodeURIComponent(String(value))}`; } export function mapValues(data: any, fn: (item: any) => any) { @@ -438,85 +350,82 @@ export function mapValues(data: any, fn: (item: any) => any) { } export function canConsumeForm(consumes: Consume[]): boolean { - for (const consume of consumes) { - if ("multipart/form-data" === consume.contentType) { - return true; + for (const consume of consumes) { + if ('multipart/form-data' === consume.contentType) { + return true; + } } - } - return false; + return false; } export interface Consume { - contentType: string; + contentType: string; } export interface RequestContext { - fetch: FetchAPI; - url: string; - init: RequestInit; + fetch: FetchAPI; + url: string; + init: RequestInit; } export interface ResponseContext { - fetch: FetchAPI; - url: string; - init: RequestInit; - response: Response; + fetch: FetchAPI; + url: string; + init: RequestInit; + response: Response; } export interface ErrorContext { - fetch: FetchAPI; - url: string; - init: RequestInit; - error: unknown; - response?: Response; + fetch: FetchAPI; + url: string; + init: RequestInit; + error: unknown; + response?: Response; } export interface Middleware { - pre?(context: RequestContext): Promise; - post?(context: ResponseContext): Promise; - onError?(context: ErrorContext): Promise; + pre?(context: RequestContext): Promise; + post?(context: ResponseContext): Promise; + onError?(context: ErrorContext): Promise; } export interface ApiResponse { - raw: Response; - value(): Promise; + raw: Response; + value(): Promise; } export interface ResponseTransformer { - (json: any): T; + (json: any): T; } export class JSONApiResponse { - constructor( - public raw: Response, - private transformer: ResponseTransformer = (jsonValue: any) => jsonValue - ) {} - - async value(): Promise { - return this.transformer(await this.raw.json()); - } + constructor(public raw: Response, private transformer: ResponseTransformer = (jsonValue: any) => jsonValue) {} + + async value(): Promise { + return this.transformer(await this.raw.json()); + } } export class VoidApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return undefined; - } + async value(): Promise { + return undefined; + } } export class BlobApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return await this.raw.blob(); - } + async value(): Promise { + return await this.raw.blob(); + }; } export class TextApiResponse { - constructor(public raw: Response) {} + constructor(public raw: Response) {} - async value(): Promise { - return await this.raw.text(); - } + async value(): Promise { + return await this.raw.text(); + }; } diff --git a/schema.json b/schema.json index f720ad6..1fb0163 100644 --- a/schema.json +++ b/schema.json @@ -1012,6 +1012,12 @@ }, "readOnly": true }, + "user_supports": { + "type": "boolean", + "nullable": true, + "description": "Return whether the user supports the bill. If the user is not authenticated\nor has not voted on this bill, return None.\n\nArgs:\n bill: The bill to check\n\nReturns:\n Whether the user supports the bill, or None if not applicable", + "readOnly": true + }, "created": { "type": "string", "format": "date-time", @@ -1043,6 +1049,7 @@ "no_votes", "pull_request", "status", + "user_supports", "yes_votes" ] }, @@ -1155,6 +1162,12 @@ }, "readOnly": true }, + "user_supports": { + "type": "boolean", + "nullable": true, + "description": "Return whether the user supports the bill. If the user is not authenticated\nor has not voted on this bill, return None.\n\nArgs:\n bill: The bill to check\n\nReturns:\n Whether the user supports the bill, or None if not applicable", + "readOnly": true + }, "created": { "type": "string", "format": "date-time", From f64d20e1d707eedc1fe4aea8fd0cea7b89d8bd41 Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 9 Mar 2024 21:18:02 -0500 Subject: [PATCH 09/11] Added session auth through github to frontend --- democrasite-frontend/.env.local | 1 - democrasite-frontend/.gitignore | 2 +- .../app/api/auth/github/callback/page.tsx | 10 +++ .../app/api/auth/github/route.ts | 41 ++++++++++++ democrasite-frontend/app/bills/[id]/page.tsx | 10 ++- democrasite-frontend/app/page.tsx | 13 ++-- democrasite-frontend/components/Bill/Bill.tsx | 1 + .../components/SignInButton/SignInButton.tsx | 11 ++++ democrasite-frontend/lib/api.ts | 62 +++++++++++++++++++ democrasite/users/api/views.py | 3 +- 10 files changed, 139 insertions(+), 15 deletions(-) delete mode 100644 democrasite-frontend/.env.local create mode 100644 democrasite-frontend/app/api/auth/github/callback/page.tsx create mode 100644 democrasite-frontend/app/api/auth/github/route.ts create mode 100644 democrasite-frontend/components/SignInButton/SignInButton.tsx create mode 100644 democrasite-frontend/lib/api.ts diff --git a/democrasite-frontend/.env.local b/democrasite-frontend/.env.local deleted file mode 100644 index 3e691a3..0000000 --- a/democrasite-frontend/.env.local +++ /dev/null @@ -1 +0,0 @@ -BASE_API_URL=http://localhost:8000/api diff --git a/democrasite-frontend/.gitignore b/democrasite-frontend/.gitignore index 97b03dd..fd3dbb5 100644 --- a/democrasite-frontend/.gitignore +++ b/democrasite-frontend/.gitignore @@ -26,7 +26,7 @@ yarn-debug.log* yarn-error.log* # local env files -# .env*.local # uncomment if sensitive environment variables added +.env*.local # vercel .vercel diff --git a/democrasite-frontend/app/api/auth/github/callback/page.tsx b/democrasite-frontend/app/api/auth/github/callback/page.tsx new file mode 100644 index 0000000..fdc570e --- /dev/null +++ b/democrasite-frontend/app/api/auth/github/callback/page.tsx @@ -0,0 +1,10 @@ +export async function getServerSideProps({ + searchParams, +}: { + searchParams: any; +}) { + await fetch( + "http://localhost:3000/api/auth/github?" + + new URLSearchParams(searchParams).toString() + ); +} diff --git a/democrasite-frontend/app/api/auth/github/route.ts b/democrasite-frontend/app/api/auth/github/route.ts new file mode 100644 index 0000000..fa52e7d --- /dev/null +++ b/democrasite-frontend/app/api/auth/github/route.ts @@ -0,0 +1,41 @@ +"use server"; + +import { cookies } from "next/headers"; +import crypto from "crypto"; +import { redirect } from "next/navigation"; +import api from "@/lib/api"; +import { NextRequest } from "next/server"; +import { revalidatePath } from "next/cache"; + +export async function POST() { + // Length was chosen randomly + const state = crypto.randomBytes(32).toString("hex"); + cookies().set("github-oauth-state", state, { + sameSite: "lax", + httpOnly: true, + secure: process.env.NODE_ENV === "production", + }); + + redirect( + `https://github.com/login/oauth/authorize?client_id=${process.env.GITHUB_CLIENT_ID}&state=${state}&scope=user:email` + ); +} + +export async function GET(request: NextRequest) { + const code = request.nextUrl.searchParams.get("code"); + const state = request.nextUrl.searchParams.get("state"); + const serverState = cookies().get("github-oauth-state"); + cookies().delete("github-oauth-state"); + + if (!code || !state || state !== serverState!.value) { + return redirect("/"); + } + + const token = await api.authApi.authGithubCreate({ + socialLogin: { code: code }, + }); + + await revalidatePath("/", "layout"); + + redirect("/"); +} diff --git a/democrasite-frontend/app/bills/[id]/page.tsx b/democrasite-frontend/app/bills/[id]/page.tsx index ce499b3..9002cf3 100644 --- a/democrasite-frontend/app/bills/[id]/page.tsx +++ b/democrasite-frontend/app/bills/[id]/page.tsx @@ -1,9 +1,7 @@ import { Container, Center } from "@mantine/core"; import { Bill } from "@/components"; -import { BillsApi } from "@/lib/auto"; - -const api = new BillsApi(); +import api from "@/lib/api"; export async function generateMetadata({ params, @@ -13,7 +11,7 @@ export async function generateMetadata({ searchParams: URLSearchParams; }) { return { - title: `${(await api.billsRetrieve({ id: params.id })).name}`, + title: `${(await api.billsApi.billsRetrieve({ id: params.id })).name}`, }; } @@ -26,7 +24,7 @@ export default async function BillDetail({
- +
@@ -34,7 +32,7 @@ export default async function BillDetail({ } export async function generateStaticParams() { - const bills = await api.billsList(); + const bills = await api.billsApi.billsList(); return bills.map((bill: any) => ({ id: bill.id.toString(), diff --git a/democrasite-frontend/app/page.tsx b/democrasite-frontend/app/page.tsx index 00c2dce..40c04df 100644 --- a/democrasite-frontend/app/page.tsx +++ b/democrasite-frontend/app/page.tsx @@ -1,12 +1,15 @@ -import { BillsApi } from "@/api/auto"; -import BillList from "@/components/BillList/BillList"; - -const api = new BillsApi(); +import api from "@/lib/api"; +import { BillList } from "@/components"; +import { SignInButton } from "@/components"; +import { cookies } from "next/headers"; export default async function Home() { + // console.log(cookies().getAll()); + // console.log(await api.billsApi.billsList()); return (
- + +
); } diff --git a/democrasite-frontend/components/Bill/Bill.tsx b/democrasite-frontend/components/Bill/Bill.tsx index 1edd5ce..0be179a 100644 --- a/democrasite-frontend/components/Bill/Bill.tsx +++ b/democrasite-frontend/components/Bill/Bill.tsx @@ -14,6 +14,7 @@ export function Bill({ bill }: { bill: Bill }) { + {bill.userSupports && "⭐️"} Bill {bill.id}: {bill.name} (PR #{bill.pullRequest.number}) diff --git a/democrasite-frontend/components/SignInButton/SignInButton.tsx b/democrasite-frontend/components/SignInButton/SignInButton.tsx new file mode 100644 index 0000000..3a14d13 --- /dev/null +++ b/democrasite-frontend/components/SignInButton/SignInButton.tsx @@ -0,0 +1,11 @@ +import { Button } from "@mantine/core"; + +export function SignInButton() { + return ( +
+ +
+ ); +} diff --git a/democrasite-frontend/lib/api.ts b/democrasite-frontend/lib/api.ts new file mode 100644 index 0000000..77396b3 --- /dev/null +++ b/democrasite-frontend/lib/api.ts @@ -0,0 +1,62 @@ +import { + AuthApi, + BillsApi, + Configuration, + ConfigurationParameters, + ResponseContext, + UsersApi, +} from "./auto"; + +class Api { + protected params: ConfigurationParameters; + config: Configuration; + authApi: AuthApi = new AuthApi(); + billsApi: BillsApi = new BillsApi(); + usersApi: UsersApi = new UsersApi(); + + constructor() { + this.params = { + basePath: process.env.BASE_API_URL, + // TODO: credentials: "include" is not working + // (see also django-cors settings, which did not immediately fix the issue but are probably necessary) + credentials: "include", + middleware: [{ post: this.propogateSessionMiddleWare.bind(this) }], + }; + this.config = new Configuration(this.params); + + this.authApi = new AuthApi(this.config); + this.billsApi = new BillsApi(this.config); + this.usersApi = new UsersApi(this.config); + } + + setCookie(cookie: string) { + this.params.headers = { + ...this.params.headers, + Cookie: cookie, + }; + this.config.config = new Configuration(this.params); + } + + async propogateSessionMiddleWare({ + url, + response, + }: ResponseContext): Promise { + if ( + response.headers.get("set-cookie") === null || + !/\/api\/auth\/.*/.test(url) + ) { + return response; + } + + response.headers.getSetCookie().forEach((cookie) => { + if (cookie.startsWith("sessionid")) { + this.setCookie(cookie); + } + }); + + return response; + } +} + +const api = new Api(); +export default api; diff --git a/democrasite/users/api/views.py b/democrasite/users/api/views.py index 2baddb6..551123c 100644 --- a/democrasite/users/api/views.py +++ b/democrasite/users/api/views.py @@ -2,7 +2,6 @@ from allauth.socialaccount.providers.oauth2.client import OAuth2Client from dj_rest_auth.registration.views import SocialLoginView from dj_rest_auth.serializers import TokenSerializer -from django.urls import reverse from drf_spectacular.utils import extend_schema from drf_spectacular.utils import extend_schema_view from rest_framework import status @@ -45,5 +44,5 @@ def me(self, request): ) class GitHubLogin(SocialLoginView): adapter_class = GitHubOAuth2Adapter - callback_url = reverse("github_callback") + callback_url = "http://localhost:3000/api/auth/github" client_class = OAuth2Client From b1621c61571b9c719b734ce2bb4120bfc5774b78 Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 9 Mar 2024 22:00:31 -0500 Subject: [PATCH 10/11] Added back debug_toolbar profiling --- config/settings/base.py | 19 ------------------- 1 file changed, 19 deletions(-) diff --git a/config/settings/base.py b/config/settings/base.py index 41bce8a..cd1b53c 100644 --- a/config/settings/base.py +++ b/config/settings/base.py @@ -303,25 +303,6 @@ "root": {"level": "INFO", "handlers": ["console"]}, } -# django-debug-toolbar -# ------------------------------------------------------------------------------ -# https://django-debug-toolbar.readthedocs.io/en/latest/configuration.html#debug-toolbar-panels -DEBUG_TOOLBAR_PANELS = [ - "debug_toolbar.panels.history.HistoryPanel", - "debug_toolbar.panels.versions.VersionsPanel", - "debug_toolbar.panels.timer.TimerPanel", - "debug_toolbar.panels.settings.SettingsPanel", - "debug_toolbar.panels.headers.HeadersPanel", - "debug_toolbar.panels.request.RequestPanel", - "debug_toolbar.panels.sql.SQLPanel", - "debug_toolbar.panels.staticfiles.StaticFilesPanel", - "debug_toolbar.panels.templates.TemplatesPanel", - "debug_toolbar.panels.cache.CachePanel", - "debug_toolbar.panels.signals.SignalsPanel", - "debug_toolbar.panels.redirects.RedirectsPanel", - # 'debug_toolbar.panels.profiling.ProfilingPanel', causes errors with frontend -] - # Celery # ------------------------------------------------------------------------------ From 84d7d26d18d97c8914dd1d6b5cb3fde4b39523fb Mon Sep 17 00:00:00 2001 From: Matthew Foster Walsh <15671892+mfosterw@users.noreply.github.com> Date: Sat, 9 Mar 2024 22:02:06 -0500 Subject: [PATCH 11/11] Minor cleanup --- democrasite-frontend/app/bills/[id]/page.tsx | 8 +------- democrasite-frontend/app/page.tsx | 1 - democrasite-frontend/components/Bill/Bill.tsx | 2 +- 3 files changed, 2 insertions(+), 9 deletions(-) diff --git a/democrasite-frontend/app/bills/[id]/page.tsx b/democrasite-frontend/app/bills/[id]/page.tsx index 9002cf3..394043e 100644 --- a/democrasite-frontend/app/bills/[id]/page.tsx +++ b/democrasite-frontend/app/bills/[id]/page.tsx @@ -3,13 +3,7 @@ import { Container, Center } from "@mantine/core"; import { Bill } from "@/components"; import api from "@/lib/api"; -export async function generateMetadata({ - params, - searchParams, -}: { - params: { id: number }; - searchParams: URLSearchParams; -}) { +export async function generateMetadata({ params }: { params: { id: number } }) { return { title: `${(await api.billsApi.billsRetrieve({ id: params.id })).name}`, }; diff --git a/democrasite-frontend/app/page.tsx b/democrasite-frontend/app/page.tsx index 40c04df..4619a63 100644 --- a/democrasite-frontend/app/page.tsx +++ b/democrasite-frontend/app/page.tsx @@ -1,7 +1,6 @@ import api from "@/lib/api"; import { BillList } from "@/components"; import { SignInButton } from "@/components"; -import { cookies } from "next/headers"; export default async function Home() { // console.log(cookies().getAll()); diff --git a/democrasite-frontend/components/Bill/Bill.tsx b/democrasite-frontend/components/Bill/Bill.tsx index 0be179a..3a942a5 100644 --- a/democrasite-frontend/components/Bill/Bill.tsx +++ b/democrasite-frontend/components/Bill/Bill.tsx @@ -14,7 +14,7 @@ export function Bill({ bill }: { bill: Bill }) { - {bill.userSupports && "⭐️"} + {bill.userSupports !== null && "⭐️"} Bill {bill.id}: {bill.name} (PR #{bill.pullRequest.number})