|
1 | 1 | import logging |
2 | 2 |
|
3 | | -from fastapi import APIRouter, BackgroundTasks, Request |
| 3 | +from fastapi import APIRouter, BackgroundTasks, Request, HTTPException |
4 | 4 | from fastapi.responses import JSONResponse |
5 | 5 | from fastapi_sqlalchemy import db |
| 6 | +from nacl.signing import VerifyKey |
| 7 | +from nacl.exceptions import BadSignatureError |
6 | 8 |
|
7 | 9 | from social.handlers_discord.base import process_event |
8 | 10 | from social.models.webhook_storage import WebhookStorage, WebhookSystems |
|
12 | 14 | router = APIRouter(prefix="/discord", tags=["webhooks"]) |
13 | 15 | settings = get_settings() |
14 | 16 | logger = logging.getLogger(__name__) |
| 17 | +verify_key = VerifyKey(bytes.fromhex(settings.DISCORD_PUBLIC_KEY)) |
15 | 18 |
|
16 | 19 |
|
17 | 20 | @router.post('') |
18 | 21 | async def discord_webhook(request: Request, background_tasks: BackgroundTasks): |
19 | 22 | """Принимает любой POST запрос от discord""" |
20 | | - request_data = await request.json() |
| 23 | + request_data: dict[str] = await request.json() |
21 | 24 | logger.debug(request_data) |
22 | 25 |
|
| 26 | + signature = request.headers.get("X-Signature-Ed25519", "") |
| 27 | + timestamp = request.headers.get("X-Signature-Timestamp", "") |
| 28 | + body = (await request.body()).decode("utf-8") |
| 29 | + |
| 30 | + try: |
| 31 | + verify_key.verify(f'{timestamp}{body}'.encode(), bytes.fromhex(signature)) |
| 32 | + except BadSignatureError: |
| 33 | + raise HTTPException(401, 'invalid request signature') |
| 34 | + |
23 | 35 | db.session.add( |
24 | 36 | WebhookStorage( |
25 | 37 | system=WebhookSystems.DISCORD, |
|
0 commit comments