From 97290049826cda03fecdc528cffc519ead920061 Mon Sep 17 00:00:00 2001 From: Sudo-JHare Date: Tue, 12 Aug 2025 20:48:52 +1000 Subject: [PATCH] Hotfix - proxy pathing --- app.py | 37 +++++++++++++++++++++++++------------ services.py | 8 ++++++-- 2 files changed, 31 insertions(+), 14 deletions(-) diff --git a/app.py b/app.py index c758362..db887ca 100644 --- a/app.py +++ b/app.py @@ -1791,25 +1791,39 @@ def proxy_hapi(subpath): logger.debug(f"Proxy received request for path: '/fhir/{subpath}', cleaned subpath: '{clean_subpath}'") # Determine the target FHIR server base URL + # NEW: Check for proxy-target query parameter first + target_server_query = request.args.get('proxy-target') target_server_header = request.headers.get('X-Target-FHIR-Server') final_base_url = None is_custom_target = False - if target_server_header: + if target_server_query: try: - parsed_url = urlparse(target_server_header) - if not parsed_url.scheme or not parsed_url.netloc: - raise ValueError("Invalid URL format in X-Target-FHIR-Server header") - final_base_url = target_server_header.rstrip('/') - is_custom_target = True - logger.info(f"Proxy target identified from header: {final_base_url}") + parsed_url = urlparse(target_server_query) + if not parsed_url.scheme or not parsed_url.netloc: + raise ValueError("Invalid URL format in proxy-target query parameter") + final_base_url = target_server_query.rstrip('/') + is_custom_target = True + logger.info(f"Proxy target identified from query parameter: {final_base_url}") except ValueError as e: - logger.warning(f"Invalid URL in X-Target-FHIR-Server header: '{target_server_header}'. Falling back. Error: {e}") - final_base_url = current_app.config['HAPI_FHIR_URL'].rstrip('/') - logger.debug(f"Falling back to default local HAPI due to invalid header: {final_base_url}") + logger.warning(f"Invalid URL in proxy-target query parameter: '{target_server_query}'. Falling back. Error: {e}") + final_base_url = current_app.config['HAPI_FHIR_URL'].rstrip('/') + logger.debug(f"Falling back to default local HAPI due to invalid query: {final_base_url}") + elif target_server_header: + try: + parsed_url = urlparse(target_server_header) + if not parsed_url.scheme or not parsed_url.netloc: + raise ValueError("Invalid URL format in X-Target-FHIR-Server header") + final_base_url = target_server_header.rstrip('/') + is_custom_target = True + logger.info(f"Proxy target identified from header: {final_base_url}") + except ValueError as e: + logger.warning(f"Invalid URL in X-Target-FHIR-Server header: '{target_server_header}'. Falling back. Error: {e}") + final_base_url = current_app.config['HAPI_FHIR_URL'].rstrip('/') + logger.debug(f"Falling back to default local HAPI due to invalid header: {final_base_url}") else: final_base_url = current_app.config['HAPI_FHIR_URL'].rstrip('/') - logger.debug(f"No target header found, proxying to default local HAPI: {final_base_url}") + logger.debug(f"No target info found, proxying to default local HAPI: {final_base_url}") # Construct the final URL for the target server request # Append the cleaned subpath only if it's not empty @@ -1891,7 +1905,6 @@ def proxy_hapi(subpath): except Exception as e: logger.error(f"Unexpected proxy error for {final_url}: {str(e)}", exc_info=True) return jsonify({'resourceType': 'OperationOutcome', 'issue': [{'severity': 'error', 'code': 'exception', 'diagnostics': 'An unexpected error occurred within the FHIR proxy.', 'details': {'text': str(e)}}]}), 500 - # --- End of corrected proxy_hapi function --- diff --git a/services.py b/services.py index 8685550..1ab917d 100644 --- a/services.py +++ b/services.py @@ -4586,16 +4586,20 @@ def retrieve_bundles(fhir_server_url, resources, output_zip, validate_references # Determine Base URL and Headers for Proxy base_proxy_url = f"{current_app.config['APP_BASE_URL'].rstrip('/')}/fhir" headers = {'Accept': 'application/fhir+json, application/fhir+xml;q=0.9, */*;q=0.8'} + is_custom_url = fhir_server_url != '/fhir' and fhir_server_url is not None and fhir_server_url.startswith('http') if is_custom_url: - headers['X-Target-FHIR-Server'] = fhir_server_url.rstrip('/') + # NEW: Add the custom URL as a query parameter for the proxy to use. + # This bypasses issues where reverse proxies might strip custom headers. + base_proxy_url = f"{base_proxy_url}?proxy-target={fhir_server_url.rstrip('/')}" + if auth_type in ['bearer', 'basic'] and auth_token: auth_display = 'Basic ' if auth_type == 'basic' else (auth_token[:10] + '...' if len(auth_token) > 10 else auth_token) yield json.dumps({"type": "info", "message": f"Using {auth_type} auth with header: Authorization: {auth_display}"}) + "\n" headers['Authorization'] = auth_token else: yield json.dumps({"type": "info", "message": "Using no authentication for custom URL"}) + "\n" - logger.debug(f"Will use proxy with X-Target-FHIR-Server: {headers['X-Target-FHIR-Server']}") + logger.debug(f"Will use proxy with proxy-target: {fhir_server_url}") else: yield json.dumps({"type": "info", "message": "Using no authentication for local HAPI server"}) + "\n" logger.debug("Will use proxy targeting local HAPI server")