Merge branch 'dev' into refactor/logging
This commit is contained in:
commit
fcc6d22e4d
26
CHANGELOG.md
Normal file
26
CHANGELOG.md
Normal file
@ -0,0 +1,26 @@
|
||||
## [1.1.1](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/compare/v1.1.0...v1.1.1) (2025-03-17)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* invalid import path for app config ([4dfbab4](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/commit/4dfbab4d4de83fbe5140c05071d8138cb09ef688))
|
||||
|
||||
# [1.1.0](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/compare/v1.0.0...v1.1.0) (2025-03-17)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **observability:** add configuration options and implement metrics/probes APIs ([d5e42d3](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/commit/d5e42d31a4ce1ac64f6c5dcf5688c0acae1fdaa6))
|
||||
* **probes:** add metrics and probes APIs for application health checks ([9754576](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/commit/9754576d28066c9805e5e4673e03fd79b3a603bd))
|
||||
|
||||
# 1.0.0 (2025-03-06)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **rabbitmq:** correct syntax for port and virtual host parameters in AsyncMQClient ([78c7217](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/commit/78c72179ec3fdb15d4af01bee15a441f0e383638))
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **notification:** add rabbitmq credentials relates notification services configs ([853d817](https://dev.azure.com/freeleaps/freeleaps-service-hub/_git/freeleaps-service-hub/commit/853d81793332513e89286d61429444d520252c27))
|
||||
@ -1,6 +1,7 @@
|
||||
from common.config.app_settings import app_settings
|
||||
from backend.content.models import DocumentDoc
|
||||
from backend.document.models import BasicProfileDoc
|
||||
from datetime import datetime, timezone
|
||||
import httpx
|
||||
import base64
|
||||
|
||||
@ -53,9 +54,12 @@ class DocumentManager:
|
||||
print(f"Failed to queue deletion: {response.text}")
|
||||
|
||||
async def cleanup_document(self):
|
||||
# Get today's date at midnight (UTC)
|
||||
today_start = datetime.now(timezone.utc).replace(hour=0, minute=0, second=0, microsecond=0)
|
||||
# Corrected query with regex
|
||||
documents = await DocumentDoc.find(
|
||||
{"created_by": {"$regex": "^content-service-"}}
|
||||
{"created_by": {"$regex": "^content-service-"},
|
||||
"create_time": {"$lt": today_start}}
|
||||
).to_list()
|
||||
|
||||
if documents:
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
from apscheduler.schedulers.asyncio import AsyncIOScheduler
|
||||
from apscheduler.triggers.date import DateTrigger
|
||||
from apscheduler.triggers.cron import CronTrigger
|
||||
from datetime import datetime, timedelta
|
||||
from scheduler.refresh_sharepoint_content_job import (
|
||||
refresh_sharepoint_content_job,
|
||||
@ -28,15 +29,11 @@ async def register_job(scheduler: AsyncIOScheduler):
|
||||
"date",
|
||||
run_date=datetime(2025, 2, 7, 20, 0, 0),
|
||||
)
|
||||
# Register cleanup_document_job as a one-time job
|
||||
# This job is just one-time job for removing many unused documents
|
||||
# Run already, now comment it out
|
||||
# await init_lock(ScheduleJobLocker.CLEANUP_DOCUMENT_JOB_LOCKER)
|
||||
# execution_time = datetime.now() + timedelta(
|
||||
# seconds=60
|
||||
# ) # Schedule to run 60 seconds from now
|
||||
# scheduler.add_job(
|
||||
# cleanup_document_job, # Job function
|
||||
# trigger=DateTrigger(run_date=execution_time), # One-time trigger
|
||||
# id="cleanup_document_one_time", # Optional: Give the job an ID
|
||||
# )
|
||||
|
||||
await init_lock(ScheduleJobLocker.CLEANUP_DOCUMENT_JOB_LOCKER)
|
||||
scheduler.add_job(
|
||||
cleanup_document_job,
|
||||
trigger=CronTrigger(hour=2, minute=0), # Runs every day at 2:00 AM
|
||||
id="cleanup_document_daily",
|
||||
)
|
||||
|
||||
|
||||
@ -86,27 +86,45 @@ class NotificationManager:
|
||||
properties: dict,
|
||||
region: Optional[UserRegion] = None,
|
||||
) -> str:
|
||||
# leverage the information in properties to enrich the message.
|
||||
message_subject = None
|
||||
message = None
|
||||
if subject.lower() == "payment":
|
||||
pass
|
||||
|
||||
# Default region to be international if not set
|
||||
# Default region to international if not set
|
||||
if region is None:
|
||||
region = UserRegion.OTHER
|
||||
|
||||
message_subject = SystemNotifications[region][subject.lower()][event.lower()][
|
||||
"message_subject"
|
||||
]
|
||||
message = SystemNotifications[region][subject.lower()][event.lower()]["message"]
|
||||
subject_lower = subject.lower()
|
||||
event_lower = event.lower()
|
||||
|
||||
if event.lower() == "authentication":
|
||||
try:
|
||||
# Get message template and subject from SystemNotifications
|
||||
notification_config = SystemNotifications[region][subject_lower][event_lower]
|
||||
message = notification_config["message"]
|
||||
message_subject = notification_config["message_subject"]
|
||||
|
||||
# Handle authentication specific formatting
|
||||
if event_lower == "authentication" and "auth_code" in properties:
|
||||
message = message.format(properties["auth_code"])
|
||||
if not message:
|
||||
raise RuntimeError("unsupported event:{}".format(event))
|
||||
|
||||
# Append content_text if it exists in properties
|
||||
if properties.get("content_text"):
|
||||
if isinstance(properties["content_text"], dict):
|
||||
# If content_text is a dictionary, use format with kwargs
|
||||
message = message.format(**properties["content_text"])
|
||||
elif isinstance(properties["content_text"], str):
|
||||
# If content_text is a string, append it with proper spacing
|
||||
content = properties["content_text"].strip()
|
||||
if message and content:
|
||||
# Use HTML line breaks for email compatibility
|
||||
message = f"{message.rstrip()}<br><br>{content}"
|
||||
else:
|
||||
# If either is empty, just use the non-empty one
|
||||
message = message or content
|
||||
|
||||
return message, message_subject
|
||||
|
||||
except KeyError as e:
|
||||
raise RuntimeError(f"Unsupported configuration - subject: {subject_lower}, event: {event_lower}, error: {str(e)}")
|
||||
except ValueError as e:
|
||||
raise RuntimeError(f"Invalid message format - error: {str(e)}")
|
||||
|
||||
async def send_in_app_notification(
|
||||
self, receiver_id: str, subject: str, event: str, properties: dict = None
|
||||
) -> None:
|
||||
|
||||
@ -14,6 +14,7 @@ from webapi.providers import metrics
|
||||
from .freeleaps_app import FreeleapsApp
|
||||
from common.config.app_settings import app_settings
|
||||
|
||||
from prometheus_fastapi_instrumentator import Instrumentator
|
||||
|
||||
def create_app() -> FastAPI:
|
||||
logging.info("App initializing")
|
||||
@ -38,6 +39,8 @@ def create_app() -> FastAPI:
|
||||
|
||||
# Call the custom_openapi function to change the OpenAPI version
|
||||
customize_openapi_security(app)
|
||||
# expose prometheus metrics
|
||||
Instrumentator().instrument(app).expose(app)
|
||||
return app
|
||||
|
||||
|
||||
|
||||
@ -25,6 +25,14 @@ class StripeManager:
|
||||
async def create_account_link(self, account_id: str, link_type: str = "account_onboarding") -> Optional[str]:
|
||||
account = stripe.Account.retrieve(account_id)
|
||||
# For account_update, try to show dashboard if TOS is accepted
|
||||
|
||||
self.module_logger.log_info("create_account_link urls",
|
||||
{
|
||||
"redirect_url": "{}/work".format(self.site_url_root),
|
||||
"refresh_url": "{}/front-door".format(self.site_url_root),
|
||||
"return_url": "{}/work".format(self.site_url_root)
|
||||
}
|
||||
)
|
||||
if link_type == "account_update" and account.tos_acceptance.date:
|
||||
login_link = stripe.Account.create_login_link(
|
||||
account_id,
|
||||
@ -284,10 +292,10 @@ class StripeManager:
|
||||
},
|
||||
},
|
||||
mode="payment",
|
||||
success_url="{}/work-space".format(
|
||||
success_url="{}/projects".format(
|
||||
self.site_url_root
|
||||
), # needs to be set, local: http://localhost/
|
||||
cancel_url="{}/work-space".format(self.site_url_root),
|
||||
cancel_url="{}/projects".format(self.site_url_root),
|
||||
)
|
||||
|
||||
if session:
|
||||
|
||||
Loading…
Reference in New Issue
Block a user