unknown commited on
Commit
86becbd
·
1 Parent(s): 13966f4
Files changed (1) hide show
  1. main.py +160 -4
main.py CHANGED
@@ -1,7 +1,163 @@
1
- from flask import Flask
 
 
 
 
 
 
2
 
3
  app = Flask(__name__)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
4
 
5
- @app.route("/")
6
- def hello():
7
- return {"hei":"success"}
 
1
+ from flask import Flask, request, jsonify
2
+ from flask_cors import CORS
3
+ from PIL import Image, ImageDraw
4
+ import io
5
+ import base64,time
6
+
7
+ from model import predict
8
 
9
  app = Flask(__name__)
10
+ CORS(app)
11
+
12
+ #global variables
13
+ threshold = 0.02
14
+ diagnosis = ''
15
+ pc_source = False
16
+
17
+ @app.route('/api/process-annotation', methods=['POST'])
18
+ def process_annotation():
19
+ try:
20
+ if request.content_type and request.content_type.startswith('multipart/form-data'):
21
+ source = request.form.get('source', 'telegram')
22
+ else:
23
+ data = request.get_json()
24
+ source = data.get('source', 'pc') if data else 'pc'
25
+
26
+ if source == "pc":
27
+
28
+ global pc_source
29
+ pc_source = True
30
+
31
+ if not data:
32
+ return jsonify({"error": "No JSON data provided"}), 400
33
+ img_data = data.get('image')
34
+ bbox = data.get('coordinates')
35
+ category = data.get('category')
36
+ view = data.get('view')
37
+
38
+ #Decode base64 image
39
+ header, encoded = img_data.split(',', 1)
40
+ img_bytes = base64.b64decode(encoded)
41
+ img = Image.open(io.BytesIO(img_bytes))
42
+
43
+ cropped = img.crop((
44
+ bbox['x'],
45
+ bbox['y'],
46
+ bbox['x'] + bbox['width'],
47
+ bbox['y'] + bbox['height']
48
+ ))
49
+ print(f"\nParameters:[Category-{category}, View-{view}, Annotations-{bbox}]\n")
50
+ print("Processing...\n")
51
+ time.sleep(2)
52
+ error = predict(cropped, view, category)
53
+ label = get_label(error)
54
+ confidence = 100 - (100 * float(error))
55
+ diagnosis = build_diagnosis(error, confidence)
56
+
57
+ draw = ImageDraw.Draw(img)
58
+ draw.rectangle(
59
+ [bbox['x'], bbox['y'], bbox['x'] + bbox['width'], bbox['y'] + bbox['height']],
60
+ outline="red", width=3
61
+ )
62
+
63
+ # Re-encode processed images to base64
64
+ buffered = io.BytesIO()
65
+ cropped.save(buffered, format="PNG")
66
+ processed_b64 = base64.b64encode(buffered.getvalue()).decode('utf-8')
67
+ processed_data_url = f"data:image/png;base64,{processed_b64}"
68
+
69
+ print(f"Results: Error-{error}, Comment-{label}, Confidence-{confidence}, Diagnosis-{diagnosis}\n")
70
+ print(f"Rendering results to: {source} \n")
71
+
72
+ return jsonify({
73
+ "processed_image": processed_data_url,
74
+ "category": category,
75
+ "comment": label,
76
+ "error": error,
77
+ "confidence": confidence,
78
+ "threshold": threshold,
79
+ "diagnosis": diagnosis
80
+ })
81
+
82
+ elif source == "telegram":
83
+ category = request.form.get('category')
84
+ view = request.form.get('view')
85
+ source_field = request.form.get('source')
86
+ image_file = request.files.get('image')
87
+
88
+ if not image_file:
89
+ return jsonify({"error": "No image file provided"}), 400
90
+
91
+ if not category or not view:
92
+ return jsonify({"error": "Missing category or view"}), 400
93
+
94
+ try:
95
+ img = Image.open(image_file)
96
+
97
+ if img.mode != 'RGB':
98
+ img = img.convert('RGB')
99
+
100
+ except Exception as e:
101
+ return jsonify({"error": f"Invalid image file: {str(e)}"}), 400
102
+
103
+ print(f"\nParameters:[Category-{category}, View-{view}, Image size-{img.size}\n")
104
+ print("Processing...\n")
105
+
106
+ error = predict(img, view, category)
107
+ label = get_label(error)
108
+ confidence = 100 - (100 * float(error))
109
+ diagnosis = build_diagnosis(error, confidence)
110
+
111
+ # Convert image back to base64 for response
112
+ buffered = io.BytesIO()
113
+ img.save(buffered, format="PNG")
114
+ processed_b64 = base64.b64encode(buffered.getvalue()).decode('utf-8')
115
+ processed_data_url = f"data:image/png;base64,{processed_b64}"
116
+
117
+ response_data = {
118
+ "processed_image": processed_data_url,
119
+ "category": category,
120
+ "view": view,
121
+ "comment": label,
122
+ "error": error,
123
+ "confidence": confidence,
124
+ "threshold": threshold,
125
+ "diagnosis": diagnosis,
126
+ "source": "telegram"
127
+ }
128
+
129
+ print(f"Results: Error-{error}, Comment-{label}, Confidence-{confidence}, Diagnosis-{diagnosis}\n")
130
+ print(f"Rendering results to: {source} \n")
131
+
132
+ return jsonify(response_data)
133
+ else:
134
+ return jsonify({"error": "Unsupported source"}), 400
135
+
136
+ except Exception as e:
137
+ print(f"Unexpected error: {e}")
138
+ return jsonify({"error": str(e)}), 500
139
+
140
+ def get_label(error):
141
+ label = "⚠️ Anomaly detected" if error > threshold else "✅ Normal structure"
142
+ return label
143
+
144
+ #RUBRIC
145
+ def build_diagnosis(error, confidence):
146
+ if confidence < 100 and confidence > 98 and error > threshold:
147
+ diagnosis = 'High probability that there is an anomaly in the structure.'
148
+ elif confidence < 98 and confidence > 96 and error > threshold:
149
+ diagnosis = 'My analysis concludes there could be an anomaly in the structure, but either the structure is not well annotated or the image could be distorted, small, unclear or bad hence the uncertainty.'
150
+ elif confidence < 96 and confidence > 92 and error > threshold:
151
+ diagnosis = 'High possibility that anomaly is false psoitive and image is greatly distorted or irrelevant. Please check the image or the annotation and try again. If results are same, consult an expert.'
152
+ elif confidence < 92 and error > threshold:
153
+ diagnosis = 'Please upload a good ultrasound scan to obtain diagnosis. I cannot recognize the image nor the outlined structure.'
154
+ elif confidence < 100 and confidence > 98 and error < threshold:
155
+ diagnosis = 'Healthy structure detected. Annotation is correct OR model partially detects healthy area.'
156
+
157
+
158
+ diagnosis += " THIS IS NOT PROFESSIONAL MEDICAL ADVICE. LIAS WITH AN EXPERT"
159
+
160
+ return diagnosis
161
 
162
+ if __name__ == '__main__':
163
+ app.run(debug=True, port=5000)