Green Doctor Deployer commited on
Commit
13bfee6
·
1 Parent(s): 3f7ebd7

Fix dictionary mapped strings for Specialist classes

Browse files
Files changed (3) hide show
  1. backend/app.py +6 -8
  2. test_hf_automated.py +82 -0
  3. test_specialist_local.py +55 -0
backend/app.py CHANGED
@@ -193,18 +193,16 @@ SPECIALIST_MAP = {
193
  "Corn (Maize) with Cercospora and Gray Leaf Spot": "Corn - Gray Leaf Spot",
194
  "Corn (Maize) with Common Rust": "Corn - Common Rust",
195
  "Corn (Maize) with Northern Leaf Blight": "Corn - Northern Leaf Blight",
196
- "Healthy Corn": "Corn - Healthy",
197
- "Grape with Black Measles": "Grape - Black Measles",
198
  "Grape with Black Rot": "Grape - Black Rot",
199
- "Grape with Leaf Blight": "Grape - Leaf Blight",
200
- "Healthy Grape": "Grape - Healthy",
 
201
  "Orange with Citrus Greening": "Orange - Citrus Greening",
202
  "Peach with Bacterial Spot": "Peach - Bacterial Spot",
203
- "Healthy Peach": "Peach - Healthy",
204
- "Pepper Bell with Bacterial Spot": "Pepper - Bacterial Spot",
205
  "Bell Pepper with Bacterial Spot": "Pepper - Bacterial Spot",
206
- "Healthy Pepper Bell": "Pepper - Healthy",
207
- "Healthy Bell Pepper": "Pepper - Healthy",
208
  "Potato with Early Blight": "Potato - Early Blight",
209
  "Potato with Late Blight": "Potato - Late Blight",
210
  "Healthy Potato Plant": "Potato - Healthy",
 
193
  "Corn (Maize) with Cercospora and Gray Leaf Spot": "Corn - Gray Leaf Spot",
194
  "Corn (Maize) with Common Rust": "Corn - Common Rust",
195
  "Corn (Maize) with Northern Leaf Blight": "Corn - Northern Leaf Blight",
196
+ "Healthy Corn (Maize) Plant": "Corn - Healthy",
 
197
  "Grape with Black Rot": "Grape - Black Rot",
198
+ "Grape with Esca (Black Measles)": "Grape - Black Measles",
199
+ "Grape with Isariopsis Leaf Spot": "Grape - Leaf Blight",
200
+ "Healthy Grape Plant": "Grape - Healthy",
201
  "Orange with Citrus Greening": "Orange - Citrus Greening",
202
  "Peach with Bacterial Spot": "Peach - Bacterial Spot",
203
+ "Healthy Peach Plant": "Peach - Healthy",
 
204
  "Bell Pepper with Bacterial Spot": "Pepper - Bacterial Spot",
205
+ "Healthy Bell Pepper Plant": "Pepper - Healthy",
 
206
  "Potato with Early Blight": "Potato - Early Blight",
207
  "Potato with Late Blight": "Potato - Late Blight",
208
  "Healthy Potato Plant": "Potato - Healthy",
test_hf_automated.py ADDED
@@ -0,0 +1,82 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import requests
2
+ import io
3
+ import time
4
+ import urllib.request
5
+ import json
6
+ from PIL import Image
7
+
8
+ API_URL = "https://rhamprassath-greendoctor-backend.hf.space/predict"
9
+
10
+ # Known URLs of raw PlantVillage images from a public repo
11
+ TEST_IMAGES = {
12
+ # Specialist Examples
13
+ "Tomato - Septoria": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Tomato___Septoria_leaf_spot/0a555f63-bf03-4958-8993-e1932b8dce9f___JR_Sept.L.S%208395.JPG",
14
+ "Tomato - Early Blight": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Tomato___Early_blight/0a0a5247-c035-42a9-aa5a-b6e828453ad2___RS_Erly.B%209425.JPG",
15
+ "Potato - Late Blight": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Potato___Late_blight/0a1a084c-ddbe-4767-a06f-13589be76228___RS_LB%202758.JPG",
16
+ "Apple - Scab": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Apple___Apple_scab/0a5e9323-dbad-432d-ac58-d291718345d9___FREC_Scab%203417.JPG",
17
+ "Corn - Common Rust": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Corn_(maize)___Common_rust_/RS_Rust%201676.JPG",
18
+ "Grape - Black Rot": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Grape___Black_rot/0a283e58-f9b6-4993-bc89-10659345712c___FAM_B.Rot%200585.JPG",
19
+ "Peach - Bacterial Spot": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Peach___Bacterial_spot/0a158b43-2df7-463d-bacc-39bf7238a204___Rutg._Bact.S%201402.JPG",
20
+
21
+ # Healthy Varieties
22
+ "Tomato - Healthy": "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Tomato___healthy/0a0bb533-5c74-4286-90ae-2fba6b364429___GH_Hlthy%209689.JPG",
23
+
24
+ # We also have Generalist classes like Rice and Wheat, but those aren't in PlantVillage exactly,
25
+ # so we will use a couple of generic links for them if needed.
26
+ "Rice - Leaf Blast": "https://upload.wikimedia.org/wikipedia/commons/e/ea/Magnaporthe_grisea.jpg",
27
+ }
28
+
29
+ def verify_all_plants():
30
+ print("Downloading & Testing PlantVillage Images against HuggingFace Engine...")
31
+ print("API Endpoint:", API_URL)
32
+ print("-" * 60)
33
+
34
+ results = []
35
+
36
+ for name, url in TEST_IMAGES.items():
37
+ try:
38
+ print(f"Downloading {name}...")
39
+ # We use urllib to handle spaces in URLs properly if any
40
+ req = urllib.request.Request(url, headers={'User-Agent': 'Mozilla/5.0'})
41
+ with urllib.request.urlopen(req) as response:
42
+ img_data = response.read()
43
+
44
+ # Post to HuggingFace
45
+ print(f"Testing {name} on HuggingFace Space...")
46
+ files = {'file': (f'{name.replace(" ", "_")}.jpg', img_data, 'image/jpeg')}
47
+
48
+ # Record time for performance metrics
49
+ start_time = time.time()
50
+ resp = requests.post(API_URL, files=files, timeout=40)
51
+ elapsed = time.time() - start_time
52
+
53
+ if resp.status_code == 200:
54
+ result = resp.json()
55
+ status_icon = "PASS" if result.get('class') != "UNKNOWN" else "WARN"
56
+ print(f"{status_icon} RESULT for {name} ({elapsed:.1f}s):")
57
+ print(f" ► Class Predicted: {result.get('class')}")
58
+ print(f" ► Confidence: {result.get('confidence', 0)*100:.1f}%")
59
+ print(f" ► AI Details: {result.get('ai_details')}")
60
+
61
+ results.append({
62
+ "Target": name,
63
+ "Predicted": result.get('class'),
64
+ "Confidence": f"{result.get('confidence', 0)*100:.1f}%",
65
+ "Expert": result.get('ai_details')
66
+ })
67
+
68
+ else:
69
+ print(f"FAILED for {name}: {resp.status_code} - {resp.text}")
70
+
71
+ except Exception as e:
72
+ print(f"Error testing {name} (Link might be dead): {e}")
73
+ print("-" * 60)
74
+ time.sleep(1) # Prevent rate limiting
75
+
76
+ print("\n\n SUMMARY REPORT:")
77
+ for r in results:
78
+ match = "MATCH" if r['Predicted'].lower().split('-')[0].strip() in r['Target'].lower() else "CONFLICT"
79
+ print(f"Target: {r['Target']:<25} | Predicted: {r['Predicted']:<25} | {r['Confidence']} | {match}")
80
+
81
+ if __name__ == "__main__":
82
+ verify_all_plants()
test_specialist_local.py ADDED
@@ -0,0 +1,55 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from transformers import AutoModelForImageClassification
2
+ import torch
3
+ import numpy as np
4
+ from PIL import Image
5
+ import requests
6
+ import io
7
+ import urllib.request
8
+
9
+ def test_local():
10
+ print("Loading MobileNetV2 locally...")
11
+ model_name = "linkanjarad/mobilenet_v2_1.0_224-plant-disease-identification"
12
+ model = AutoModelForImageClassification.from_pretrained(model_name).to(torch.float32)
13
+ model.eval()
14
+
15
+ print("Fetching sample Tomato Septoria image...")
16
+ url = "https://raw.githubusercontent.com/spMohanty/PlantVillage-Dataset/master/raw/color/Tomato___Septoria_leaf_spot/0a555f63-bf03-4958-8993-e1932b8dce9f___JR_Sept.L.S%208395.JPG"
17
+
18
+ req = urllib.request.Request(url, headers={'User-Agent': 'Mozilla/5.0'})
19
+ try:
20
+ with urllib.request.urlopen(req) as response:
21
+ img_data = response.read()
22
+ image = Image.open(io.BytesIO(img_data)).convert("RGB").resize((224, 224))
23
+ except Exception as e:
24
+ print("Could not download image. Creating a synthetic green image with black spots...")
25
+ image = Image.new('RGB', (224, 224), color=(30, 150, 30))
26
+ # draw spots
27
+ for _ in range(100):
28
+ x, y = np.random.randint(0, 224, 2)
29
+ for i in range(3):
30
+ for j in range(3):
31
+ if x+i<224 and y+j<224:
32
+ image.putpixel((x+i, y+j), (50, 20, 0))
33
+
34
+ img_array = np.array(image).astype(np.float32) / 255.0
35
+ mean = np.array([0.5, 0.5, 0.5])
36
+ std = np.array([0.5, 0.5, 0.5])
37
+ img_array = (img_array - mean) / std
38
+ img_array = img_array.transpose(2, 0, 1)
39
+ inputs = torch.tensor(img_array, dtype=torch.float32).unsqueeze(0)
40
+
41
+ with torch.no_grad():
42
+ outputs = model(inputs)
43
+
44
+ probs = torch.nn.functional.softmax(outputs.logits, dim=-1)[0]
45
+
46
+ print("\n--- TOP 3 PREDICTIONS ---")
47
+ top3 = torch.topk(probs, 3)
48
+ for i in range(3):
49
+ idx = top3.indices[i].item()
50
+ score = top3.values[i].item()
51
+ label = model.config.id2label[idx]
52
+ print(f"{i+1}. {label} : {score*100:.2f}%")
53
+
54
+ if __name__ == "__main__":
55
+ test_local()