mgbam commited on
Commit
dc83e12
·
verified ·
1 Parent(s): aac4d20

Update modules/orchestrator.py

Browse files
Files changed (1) hide show
  1. modules/orchestrator.py +80 -0
modules/orchestrator.py CHANGED
@@ -0,0 +1,80 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # modules/orchestrator.py
2
+ """
3
+ The main conductor. This module sequences the calls to APIs and the AI model.
4
+ It's the heart of the application's logic.
5
+ """
6
+ import asyncio
7
+ import aiohttp
8
+ import ast
9
+ from . import gemini_handler, prompts
10
+ from .api_clients import umls_client, pubmed_client
11
+
12
+ async def run_symptom_synthesis(user_query: str, image_input=None):
13
+ """
14
+ The complete pipeline for the Symptom Synthesizer tab.
15
+ """
16
+ if not user_query:
17
+ return "Please enter your symptoms or query."
18
+
19
+ # --- Step 1: Extract Key Concepts with Gemini ---
20
+ term_extraction_prompt = prompts.get_term_extraction_prompt(user_query)
21
+ concepts_str = await gemini_handler.generate_gemini_response(term_extraction_prompt)
22
+ try:
23
+ # Safely evaluate the string representation of the list
24
+ concepts = ast.literal_eval(concepts_str)
25
+ if not isinstance(concepts, list):
26
+ concepts = [user_query] # Fallback
27
+ except (ValueError, SyntaxError):
28
+ concepts = [user_query] # Fallback if Gemini doesn't return a perfect list
29
+
30
+ search_query = " AND ".join(concepts)
31
+
32
+ # --- Step 2: Gather Evidence Asynchronously ---
33
+ async with aiohttp.ClientSession() as session:
34
+ # Create a UMLS client instance for this session
35
+ umls = umls_client.UMLSClient(session)
36
+
37
+ # Define all async tasks
38
+ tasks = {
39
+ "pubmed": pubmed_client.search_pubmed(session, search_query, max_results=3),
40
+ "umls_cui": umls.get_cui_for_term(concepts[0] if concepts else user_query),
41
+ # Add other clients here as they are built e.g.,
42
+ # "trials": clinicaltrials_client.find_trials(session, search_query),
43
+ # "fda": openfda_client.get_adverse_events(session, concepts)
44
+ }
45
+
46
+ # Run all tasks concurrently
47
+ results = await asyncio.gather(*tasks.values(), return_exceptions=True)
48
+
49
+ # Map results back to their keys, handling potential errors
50
+ api_data = dict(zip(tasks.keys(), results))
51
+ for key, value in api_data.items():
52
+ if isinstance(value, Exception):
53
+ print(f"Error fetching data from {key}: {value}")
54
+ api_data[key] = None # Nullify data if fetch failed
55
+
56
+ # --- Step 3: Format Data for the Synthesis Prompt ---
57
+ # Convert raw JSON/list data into clean, readable strings for the AI
58
+ pubmed_formatted = "\n".join([f"- Title: {a.get('title', 'N/A')}, PMID: {a.get('uid', 'N/A')}" for a in api_data.get('pubmed', [])])
59
+
60
+ # In a real implementation, you'd format trials and fda data here too
61
+ trials_formatted = "Trial data fetching is not yet fully implemented in this demo."
62
+ fda_formatted = "FDA data fetching is not yet fully implemented in this demo."
63
+
64
+
65
+ # --- Step 4: The Grand Synthesis with Gemini ---
66
+ synthesis_prompt = prompts.get_synthesis_prompt(
67
+ user_query,
68
+ concepts,
69
+ pubmed_data=pubmed_formatted,
70
+ trials_data=trials_formatted,
71
+ fda_data=fda_formatted
72
+ )
73
+
74
+ final_report = await gemini_handler.generate_gemini_response(synthesis_prompt)
75
+
76
+ # --- Step 5: Prepend Disclaimer and Return ---
77
+ return f"{prompts.DISCLAIMER}\n\n{final_report}"
78
+
79
+ # You would create similar orchestrator functions for other tabs
80
+ # e.g., async def run_drug_interaction_analysis(drug_list): ...