Mohibullah commited on
Commit
e898f0a
·
1 Parent(s): c90ac52

Use live retrieval result instead of Neuroxen fallback

Browse files
Files changed (1) hide show
  1. gradio_pharmacopilot_demo.py +28 -10
gradio_pharmacopilot_demo.py CHANGED
@@ -2,6 +2,7 @@ from __future__ import annotations
2
 
3
  import json
4
  import os
 
5
  import time
6
  from difflib import SequenceMatcher, get_close_matches
7
  from pathlib import Path
@@ -94,7 +95,9 @@ SESSION_SEARCHES = 0
94
 
95
 
96
  def normalize(text: str) -> str:
97
- return " ".join((text or "").strip().lower().split())
 
 
98
 
99
 
100
  def clean_prediction(raw_prediction: str) -> str:
@@ -128,12 +131,11 @@ def label_for_medicine(ocr_text: str, medicine: dict[str, Any]) -> str:
128
  return brands[0] if brands else medicine["name"]
129
 
130
 
131
- def find_medicine_from_ocr(ocr_text: str) -> tuple[dict[str, Any], list[dict[str, Any]], str]:
132
  query = normalize(ocr_text)
133
  corrected_query = query
134
  canonical = BD_BRAND_TO_GENERIC.get(corrected_query, corrected_query)
135
- medicine = MED_BY_NAME.get(normalize(canonical)) or MED_BY_NAME.get("naproxen") or MEDICINES[0]
136
- display_name = label_for_medicine(ocr_text, medicine)
137
 
138
  candidate_names = set()
139
  for med in MEDICINES:
@@ -152,7 +154,21 @@ def find_medicine_from_ocr(ocr_text: str) -> tuple[dict[str, Any], list[dict[str
152
  scored.append({"label": name, "medicine": med, "score": score})
153
 
154
  scored.sort(key=lambda item: item["score"], reverse=True)
155
- top = [{"label": display_name, "medicine": medicine, "score": 0.97}]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
156
  seen_ids = {medicine["id"]}
157
  for item in scored:
158
  if item["medicine"]["id"] in seen_ids:
@@ -173,7 +189,8 @@ def find_medicine_from_ocr(ocr_text: str) -> tuple[dict[str, Any], list[dict[str
173
  continue
174
  break
175
 
176
- return medicine, top, display_name
 
177
 
178
 
179
  def get_inventory(medicine: dict[str, Any]) -> dict[str, Any]:
@@ -291,6 +308,7 @@ def medicine_details_html(
291
  inventory: dict[str, Any],
292
  ocr_text: str,
293
  display_name: str,
 
294
  ) -> str:
295
  return f"""
296
  <div class="result-card">
@@ -300,7 +318,7 @@ def medicine_details_html(
300
  <dt>Generic</dt><dd>{medicine.get('name', 'Unknown')}</dd>
301
  <dt>Strength</dt><dd>{first_strength(medicine.get('strength', ''))}</dd>
302
  <dt>Manufacturer</dt><dd>{medicine.get('manufacturer') or 'Not listed'}</dd>
303
- <dt>Confidence</dt><dd>97%</dd>
304
  <dt>Category</dt><dd>{medicine.get('category', 'General')}</dd>
305
  <dt>Price</dt><dd>PKR 145</dd>
306
  </dl>
@@ -421,7 +439,7 @@ def analyze_prescription(image, progress=gr.Progress()):
421
  progress(pct, desc=label)
422
  time.sleep(0.25)
423
 
424
- medicine, candidates, display_name = find_medicine_from_ocr(ocr_text)
425
  inventory = get_inventory(medicine)
426
  image_path = resolve_asset_path(medicine.get("image_path"))
427
  package_image = str(image_path) if image_path else None
@@ -438,10 +456,10 @@ def analyze_prescription(image, progress=gr.Progress()):
438
  return (
439
  load_kpi_metrics(SESSION_SEARCHES),
440
  pipeline_html(5),
441
- medicine_details_html(medicine, inventory, ocr_text, display_name),
442
  package_image,
443
  package_status_html(inventory),
444
- confidence_gauge(97),
445
  candidates_html(candidates),
446
  ocr_compare_html(medicine, ocr_text, display_name),
447
  gr.update(visible=True),
 
2
 
3
  import json
4
  import os
5
+ import unicodedata
6
  import time
7
  from difflib import SequenceMatcher, get_close_matches
8
  from pathlib import Path
 
95
 
96
 
97
  def normalize(text: str) -> str:
98
+ text = unicodedata.normalize("NFKD", str(text or ""))
99
+ text = "".join(ch for ch in text if not unicodedata.combining(ch))
100
+ return " ".join(text.strip().lower().split())
101
 
102
 
103
  def clean_prediction(raw_prediction: str) -> str:
 
131
  return brands[0] if brands else medicine["name"]
132
 
133
 
134
+ def find_medicine_from_ocr(ocr_text: str) -> tuple[dict[str, Any], list[dict[str, Any]], str, int]:
135
  query = normalize(ocr_text)
136
  corrected_query = query
137
  canonical = BD_BRAND_TO_GENERIC.get(corrected_query, corrected_query)
138
+ direct_medicine = MED_BY_NAME.get(normalize(canonical))
 
139
 
140
  candidate_names = set()
141
  for med in MEDICINES:
 
154
  scored.append({"label": name, "medicine": med, "score": score})
155
 
156
  scored.sort(key=lambda item: item["score"], reverse=True)
157
+ if direct_medicine:
158
+ medicine = direct_medicine
159
+ display_name = label_for_medicine(ocr_text, medicine)
160
+ primary_score = 0.97
161
+ elif scored:
162
+ best = scored[0]
163
+ medicine = best["medicine"]
164
+ display_name = best["label"]
165
+ primary_score = best["score"]
166
+ else:
167
+ medicine = MEDICINES[0]
168
+ display_name = clean_prediction(ocr_text) or "Needs review"
169
+ primary_score = 0.0
170
+
171
+ top = [{"label": display_name, "medicine": medicine, "score": primary_score}]
172
  seen_ids = {medicine["id"]}
173
  for item in scored:
174
  if item["medicine"]["id"] in seen_ids:
 
189
  continue
190
  break
191
 
192
+ confidence = max(0, min(99, round(primary_score * 100)))
193
+ return medicine, top, display_name, confidence
194
 
195
 
196
  def get_inventory(medicine: dict[str, Any]) -> dict[str, Any]:
 
308
  inventory: dict[str, Any],
309
  ocr_text: str,
310
  display_name: str,
311
+ confidence: int,
312
  ) -> str:
313
  return f"""
314
  <div class="result-card">
 
318
  <dt>Generic</dt><dd>{medicine.get('name', 'Unknown')}</dd>
319
  <dt>Strength</dt><dd>{first_strength(medicine.get('strength', ''))}</dd>
320
  <dt>Manufacturer</dt><dd>{medicine.get('manufacturer') or 'Not listed'}</dd>
321
+ <dt>Confidence</dt><dd>{confidence}%</dd>
322
  <dt>Category</dt><dd>{medicine.get('category', 'General')}</dd>
323
  <dt>Price</dt><dd>PKR 145</dd>
324
  </dl>
 
439
  progress(pct, desc=label)
440
  time.sleep(0.25)
441
 
442
+ medicine, candidates, display_name, confidence = find_medicine_from_ocr(ocr_text)
443
  inventory = get_inventory(medicine)
444
  image_path = resolve_asset_path(medicine.get("image_path"))
445
  package_image = str(image_path) if image_path else None
 
456
  return (
457
  load_kpi_metrics(SESSION_SEARCHES),
458
  pipeline_html(5),
459
+ medicine_details_html(medicine, inventory, ocr_text, display_name, confidence),
460
  package_image,
461
  package_status_html(inventory),
462
+ confidence_gauge(confidence),
463
  candidates_html(candidates),
464
  ocr_compare_html(medicine, ocr_text, display_name),
465
  gr.update(visible=True),