Initial commit: CI Agent competitive-intelligence monitoring app
FastAPI + Celery + Next.js + Postgres/Redis app with company monitoring, source collection, LLM-based change analysis, enrichment, and account security (Turnstile, escalating lockout, email verification).
This commit is contained in:
@@ -0,0 +1,50 @@
|
||||
"""Telnyx SMS provider via Telnyx's Programmable Messaging REST API (no SDK
|
||||
dependency - just a Bearer-authenticated POST), mirroring twilio_sms.py's
|
||||
shape. No-ops with a clear error if Telnyx isn't configured; the caller
|
||||
(alert_service) is what additionally gates on `NOTIFICATION_SMS_ENABLED`
|
||||
before ever constructing this provider.
|
||||
"""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import httpx
|
||||
|
||||
from app.core.config import Settings
|
||||
from app.notifications.base import DeliveryResult, NotificationMessage
|
||||
|
||||
_API_URL = "https://api.telnyx.com/v2/messages"
|
||||
|
||||
|
||||
class TelnyxSmsProvider:
|
||||
provider_name = "telnyx_sms"
|
||||
|
||||
def __init__(self, settings: Settings) -> None:
|
||||
self._settings = settings
|
||||
|
||||
async def send(self, message: NotificationMessage) -> DeliveryResult:
|
||||
settings = self._settings
|
||||
if not (settings.telnyx_api_key and settings.telnyx_from_number):
|
||||
return DeliveryResult(success=False, error="Telnyx is not configured")
|
||||
|
||||
try:
|
||||
async with httpx.AsyncClient(timeout=15) as client:
|
||||
response = await client.post(
|
||||
_API_URL,
|
||||
headers={"Authorization": f"Bearer {settings.telnyx_api_key}"},
|
||||
json={
|
||||
"from": settings.telnyx_from_number,
|
||||
"to": message.destination_value,
|
||||
"text": message.body_text,
|
||||
},
|
||||
)
|
||||
except httpx.HTTPError as exc:
|
||||
return DeliveryResult(success=False, error=str(exc))
|
||||
|
||||
data = response.json()
|
||||
if response.status_code >= 400:
|
||||
errors = data.get("errors") or []
|
||||
detail = errors[0].get("detail") if errors else response.text[:200]
|
||||
return DeliveryResult(
|
||||
success=False, error=f"Telnyx error {response.status_code}: {detail}"
|
||||
)
|
||||
return DeliveryResult(success=True, external_message_id=data.get("data", {}).get("id"))
|
||||
Reference in New Issue
Block a user