From 51063d5d5e14dd4937081b45386caf43dfeefb28 Mon Sep 17 00:00:00 2001 From: Proudlock <270015376@geaerospace.com> Date: Wed, 9 Sep 2026 09:40:14 -0400 Subject: [PATCH] Add machine relationship to operator report email alerts - Query AssetRelationship to find if PC has a machine relationship - Subject line now shows: "Operator Issue Report: HOSTNAME (Machine #6906)" - Email body includes machine name and number as clickable link - Machine info only appears if relationship exists --- plugins/endpoints/api/routes.py | 38 ++++++++++++++++++++++++++++++++- 1 file changed, 37 insertions(+), 1 deletion(-) diff --git a/plugins/endpoints/api/routes.py b/plugins/endpoints/api/routes.py index 2b7dbbc3..d816713b 100644 --- a/plugins/endpoints/api/routes.py +++ b/plugins/endpoints/api/routes.py @@ -2941,6 +2941,7 @@ def _send_operator_report_alert(report, asset_id, hostname): """Send email alert for new operator issue report to default alert recipients.""" from flask import url_for, request from shopdb.utils.mailer import get_smtp_config, _normalize_recipients + from shopdb.core.models.relationship import AssetRelationship current_app.logger.info('_send_operator_report_alert called for report %d, asset %d, hostname %s', report.operatorreportid, asset_id, hostname) @@ -2960,6 +2961,24 @@ def _send_operator_report_alert(report, asset_id, hostname): current_app.logger.warning('Cannot send operator report alert: asset %d not found', asset_id) return + # Check if this PC has a relationship to a machine + machine_relationship = ( + AssetRelationship.query + .filter_by(sourceassetid=asset_id) + .filter(AssetRelationship.label.like('%machine%')) + .first() + ) + + machine_info = None + if machine_relationship: + machine_asset = Asset.query.get(machine_relationship.targetassetid) + if machine_asset: + machine_info = { + 'assetid': machine_asset.assetid, + 'assetnumber': machine_asset.assetnumber, + 'name': machine_asset.name + } + # Generate absolute URL to frontend page (not API endpoint) try: scheme = request.scheme if request else 'https' @@ -2988,6 +3007,22 @@ def _send_operator_report_alert(report, asset_id, hostname): safe_reason = escape(report.reason) safe_details = escape(report.details or 'No additional details provided.') + # Build machine info for subject and body + machine_subject_part = '' + machine_body_line = '' + if machine_info: + safe_machine_number = escape(machine_info['assetnumber'] or 'N/A') + safe_machine_name = escape(machine_info['name'] or safe_machine_number) + try: + scheme = request.scheme if request else 'https' + host = request.host if request else 'localhost' + machine_url = f'{scheme}://{host}/shopdb/machines/{machine_info["assetid"]}' + except Exception: + machine_url = f'https://localhost/shopdb/machines/{machine_info["assetid"]}' + + machine_subject_part = f' (Machine #{safe_machine_number})' + machine_body_line = f'
Machine: {safe_machine_name} (#{safe_machine_number})
' + # Build HTML body (don't use render_email to avoid subject duplication) html_body = f'''New Issue Report from Shop Floor
Device: {safe_name} ({safe_hostname})
Asset Number: {safe_assetnumber}
+ {machine_body_line}Reason: {safe_reason}
Reported: {escape(reported_at)}