mirror of
https://github.com/GSA/notifications-api.git
synced 2026-09-11 10:28:55 -04:00
Restructured the query to be adhering to SQLAlchemy 2.0.
Signed-off-by: Cliff Hill <Clifford.hill@gsa.gov>
This commit is contained in:
@@ -1,9 +1,10 @@
|
|||||||
from datetime import date, timedelta
|
from datetime import date, timedelta
|
||||||
|
|
||||||
from sqlalchemy import Date, case, func
|
from sqlalchemy import Date, case, func, select, union_all, cast
|
||||||
from sqlalchemy.dialects.postgresql import insert
|
from sqlalchemy.dialects.postgresql import insert
|
||||||
|
from sqlalchemy.orm import aliased
|
||||||
from sqlalchemy.sql.expression import extract, literal
|
from sqlalchemy.sql.expression import extract, literal
|
||||||
from sqlalchemy.types import DateTime, Integer
|
from sqlalchemy.types import DateTime, Integer, Text
|
||||||
|
|
||||||
from app import db
|
from app import db
|
||||||
from app.dao.dao_utils import autocommit
|
from app.dao.dao_utils import autocommit
|
||||||
@@ -126,83 +127,96 @@ def fetch_notification_status_for_service_for_day(fetch_day, service_id):
|
|||||||
|
|
||||||
|
|
||||||
def fetch_notification_status_for_service_for_today_and_7_previous_days(
|
def fetch_notification_status_for_service_for_today_and_7_previous_days(
|
||||||
service_id, by_template=False, limit_days=7
|
service_id: str,
|
||||||
):
|
by_template: bool = False,
|
||||||
|
limit_days: int = 7
|
||||||
|
) -> list[dict | None]:
|
||||||
start_date = midnight_n_days_ago(limit_days)
|
start_date = midnight_n_days_ago(limit_days)
|
||||||
now = utc_now()
|
now = utc_now()
|
||||||
stats_for_7_days = db.session.query(
|
|
||||||
FactNotificationStatus.notification_type.cast(db.Text).label(
|
# Query for the last 7 days
|
||||||
"notification_type"
|
stats_for_7_days = select(
|
||||||
),
|
cast(FactNotificationStatus.notification_type, Text).label("notification_type"),
|
||||||
FactNotificationStatus.notification_status.cast(db.Text).label("status"),
|
cast(FactNotificationStatus.notification_status, Text).label("status"),
|
||||||
*(
|
*(
|
||||||
[
|
[
|
||||||
FactNotificationStatus.template_id.label("template_id"),
|
FactNotificationStatus.template_id.label("template_id"),
|
||||||
FactNotificationStatus.local_date.label("last_used"),
|
FactNotificationStatus.local_date.label("date_used"),
|
||||||
]
|
] if by_template else []
|
||||||
if by_template
|
|
||||||
else []
|
|
||||||
),
|
),
|
||||||
FactNotificationStatus.notification_count.label("count"),
|
FactNotificationStatus.notification_count.label("count"),
|
||||||
).filter(
|
).where(
|
||||||
FactNotificationStatus.service_id == service_id,
|
FactNotificationStatus.service_id == service_id,
|
||||||
FactNotificationStatus.local_date >= start_date,
|
FactNotificationStatus.local_date >= start_date,
|
||||||
FactNotificationStatus.key_type != KeyType.TEST,
|
FactNotificationStatus.key_type != KeyType.TEST,
|
||||||
)
|
)
|
||||||
|
|
||||||
stats_for_today = (
|
# Query for today's stats
|
||||||
db.session.query(
|
stats_for_today = select(
|
||||||
Notification.notification_type.cast(db.Text),
|
cast(Notification.notification_type, Text),
|
||||||
Notification.status.cast(db.Text),
|
cast(Notification.status, Text),
|
||||||
*(
|
*(
|
||||||
[
|
[
|
||||||
Notification.template_id,
|
Notification.template_id,
|
||||||
literal(date.today()).label("last_used"),
|
literal(date.today()).label("date_used"),
|
||||||
]
|
] if by_template else []
|
||||||
if by_template
|
),
|
||||||
else []
|
func.count().label("count"),
|
||||||
),
|
).where(
|
||||||
func.count().label("count"),
|
Notification.created_at >= get_midnight_in_utc(now),
|
||||||
)
|
Notification.service_id == service_id,
|
||||||
.filter(
|
Notification.key_type != KeyType.TEST,
|
||||||
Notification.created_at >= get_midnight_in_utc(now),
|
).group_by(
|
||||||
Notification.service_id == service_id,
|
Notification.notification_type,
|
||||||
Notification.key_type != KeyType.TEST,
|
*([Notification.template_id] if by_template else []),
|
||||||
)
|
Notification.status,
|
||||||
.group_by(
|
|
||||||
Notification.notification_type,
|
|
||||||
*([Notification.template_id] if by_template else []),
|
|
||||||
Notification.status,
|
|
||||||
)
|
|
||||||
)
|
)
|
||||||
|
|
||||||
all_stats_table = stats_for_7_days.union_all(stats_for_today).subquery()
|
# Combine the queries using union_all
|
||||||
|
all_stats_union = union_all(stats_for_7_days, stats_for_today).subquery()
|
||||||
|
all_stats_alias = aliased(all_stats_union)
|
||||||
|
|
||||||
query = db.session.query(
|
# Final query with optional template joins
|
||||||
|
query = select(
|
||||||
*(
|
*(
|
||||||
[
|
[
|
||||||
Template.name.label("template_name"),
|
Template.name.label("template_name"),
|
||||||
False, # TODO: this is related to is_precompiled_letter
|
False, # TODO: Handle `is_precompiled_letter`
|
||||||
all_stats_table.c.template_id,
|
all_stats_alias.c.template_id,
|
||||||
Template.folder.name.label("folder"),
|
Template.folder.label("folder"),
|
||||||
Template.created_by.name.label("created_by"),
|
Template.created_by.label("created_by"),
|
||||||
]
|
func.max(all_stats_alias.c.date_used).label("last_used"), # Get the most recent date
|
||||||
if by_template
|
] if by_template else []
|
||||||
else []
|
|
||||||
),
|
),
|
||||||
all_stats_table.c.notification_type,
|
all_stats_alias.c.notification_type,
|
||||||
all_stats_table.c.status,
|
all_stats_alias.c.status,
|
||||||
func.cast(func.sum(all_stats_table.c.count), Integer).label("count"),
|
cast(func.sum(all_stats_alias.c.count), Integer).label("count"),
|
||||||
)
|
)
|
||||||
|
|
||||||
if by_template:
|
if by_template:
|
||||||
query = query.filter(all_stats_table.c.template_id == Template.id)
|
query = query.join(Template, all_stats_alias.c.template_id == Template.id)
|
||||||
|
|
||||||
return query.group_by(
|
# Group by all necessary fields except date_used
|
||||||
*([Template.name, all_stats_table.c.template_id] if by_template else []),
|
query = query.group_by(
|
||||||
all_stats_table.c.notification_type,
|
*(
|
||||||
all_stats_table.c.status,
|
[
|
||||||
).all()
|
Template.name,
|
||||||
|
all_stats_alias.c.template_id,
|
||||||
|
Template.folder,
|
||||||
|
Template.created_by,
|
||||||
|
] if by_template else []
|
||||||
|
),
|
||||||
|
all_stats_alias.c.notification_type,
|
||||||
|
all_stats_alias.c.status,
|
||||||
|
)
|
||||||
|
|
||||||
|
print("*"*79)
|
||||||
|
print(query)
|
||||||
|
print("*"*79)
|
||||||
|
|
||||||
|
# Execute the query using Flask-SQLAlchemy's session
|
||||||
|
result = db.session.execute(query)
|
||||||
|
return result.mappings().all()
|
||||||
|
|
||||||
|
|
||||||
def fetch_notification_status_totals_for_all_services(start_date, end_date):
|
def fetch_notification_status_totals_for_all_services(start_date, end_date):
|
||||||
|
|||||||
Reference in New Issue
Block a user