Skip to content

Commit

Permalink
[WEBHOOK]: Initial integration
Browse files Browse the repository at this point in the history
  • Loading branch information
amadolid committed Oct 18, 2024
1 parent 8192969 commit 5309d45
Show file tree
Hide file tree
Showing 8 changed files with 125 additions and 4 deletions.
10 changes: 8 additions & 2 deletions jac-cloud/jac_cloud/jaseci/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,10 +61,16 @@ async def lifespan(app: _FaststAPI) -> AsyncGenerator[None, _FaststAPI]:

populate_yaml_specs(cls.__app__)

from .routers import healthz_router, sso_router, user_router
from .routers import healthz_router, sso_router, user_router, webhook_router
from ..plugin.jaseci import walker_router

for router in [healthz_router, sso_router, user_router, walker_router]:
for router in [
healthz_router,
sso_router,
user_router,
walker_router,
webhook_router,
]:
cls.__app__.include_router(router)

@cls.__app__.exception_handler(Exception)
Expand Down
2 changes: 2 additions & 0 deletions jac-cloud/jac_cloud/jaseci/dtos/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
UserResetPassword,
UserVerification,
)
from .webhook import GenerateKey


__all__ = [
Expand All @@ -18,4 +19,5 @@
"UserRequest",
"UserResetPassword",
"UserVerification",
"GenerateKey",
]
24 changes: 24 additions & 0 deletions jac-cloud/jac_cloud/jaseci/dtos/webhook.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
"""Jaseci User DTOs."""

from typing import Literal

from annotated_types import Len

from pydantic import BaseModel, Field

from typing_extensions import Annotated


class Expiration(BaseModel):
"""Key Expiration."""

count: Annotated[int, Field(strict=True, gt=0, default=60)] = 60
interval: Literal["seconds", "minutes", "hours", "days"] = "days"


class GenerateKey(BaseModel):
"""User Creation Request Model."""

walkers: Annotated[list[str], Len(min_length=1)]
nodes: list[str] = Field(default_factory=list)
expiration: Expiration = Field(default_factory=Expiration)
3 changes: 2 additions & 1 deletion jac-cloud/jac_cloud/jaseci/models/__init__.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
"""Jaseci Models."""

from .user import NO_PASSWORD, User
from .webhook import Webhook

__all__ = ["NO_PASSWORD", "User"]
__all__ = ["NO_PASSWORD", "User", "Webhook"]
53 changes: 53 additions & 0 deletions jac-cloud/jac_cloud/jaseci/models/webhook.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
"""Jaseci Models."""

from dataclasses import dataclass
from datetime import datetime
from typing import Any, Generator, Mapping, cast

from bson import ObjectId

from ..datasources.collection import Collection as BaseCollection


@dataclass(kw_only=True)
class Webhook:
"""User Base Model."""

id: ObjectId
root_id: ObjectId
walkers: list[str]
nodes: list[str]
expiration: datetime
key: str

class Collection(BaseCollection["Webhook"]):
"""
User collection interface.
This interface is for User's Management.
You may override this if you wish to implement different structure
"""

__collection__ = "webhook"
__indexes__ = [{"keys": ["token"], "unique": True}]

@classmethod
def __document__(cls, doc: Mapping[str, Any]) -> "Webhook":
"""
Return parsed Webhook from document.
This the default User parser after getting a single document.
You may override this to specify how/which class it will be casted/based.
"""
doc = cast(dict, doc)
return Webhook(id=doc.pop("_id"), **doc)

@classmethod
def find_by_root_id(cls, root_id: ObjectId) -> Generator["Webhook", None, None]:
"""Retrieve webhook via root_id."""
return cls.find({"root_id": root_id})

@classmethod
def find_by_key(cls, key: str) -> "Webhook | None":
"""Retrieve webhook via root_id."""
return cls.find_one({"key": key})
3 changes: 2 additions & 1 deletion jac-cloud/jac_cloud/jaseci/routers/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,5 +3,6 @@
from .healthz import router as healthz_router
from .sso import router as sso_router
from .user import router as user_router
from .webhook import router as webhook_router

__all__ = ["healthz_router", "sso_router", "user_router"]
__all__ = ["healthz_router", "sso_router", "user_router", "webhook_router"]
30 changes: 30 additions & 0 deletions jac-cloud/jac_cloud/jaseci/routers/webhook.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
"""User APIs."""

from fastapi import APIRouter, Request, status
from fastapi.exceptions import HTTPException
from fastapi.responses import ORJSONResponse

from passlib.hash import pbkdf2_sha512

from ..dtos import GenerateKey
from ..models import Webhook
from ..security import (
authenticator,
create_code,
create_token,
invalidate_token,
verify_code,
)

router = APIRouter(prefix="/webhook", tags=["webhook"])


@router.post(
"/generate-key", status_code=status.HTTP_201_CREATED, dependencies=authenticator
)
def generate_key(req: GenerateKey) -> ORJSONResponse:
"""Generate key API."""
import pdb

pdb.set_trace()
return ORJSONResponse(content={"token": 1, "user": 1})
4 changes: 4 additions & 0 deletions jac-cloud/jac_cloud/plugin/jaseci.py
Original file line number Diff line number Diff line change
Expand Up @@ -263,6 +263,7 @@ def specs(
excluded: str | list[str] = [], # noqa: B006
auth: bool = True,
private: bool = False,
is_webhook: bool = False,
) -> Callable:
"""Walker Decorator."""

Expand All @@ -274,6 +275,7 @@ def wrapper(cls: Type[WalkerArchitype]) -> Type[WalkerArchitype]:
ex = excluded
a = auth
pv = private
iw = is_webhook

class __specs__(DefaultSpecs): # noqa: N801
path: str = p
Expand All @@ -282,6 +284,7 @@ class __specs__(DefaultSpecs): # noqa: N801
excluded: str | list[str] = ex
auth: bool = a
private: bool = pv
is_webhook: bool = iw

cls.__specs__ = __specs__ # type: ignore[attr-defined]

Expand All @@ -303,6 +306,7 @@ class DefaultSpecs:
excluded: str | list[str] = []
auth: bool = True
private: bool = False
is_webhook: bool = False


class JacAccessValidationPlugin:
Expand Down

0 comments on commit 5309d45

Please sign in to comment.