ShutterStack commited on
Commit
f09c839
·
verified ·
1 Parent(s): 8e35844

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +154 -64
app.py CHANGED
@@ -11,28 +11,58 @@ import numpy as np
11
  import json
12
  import sqlite3
13
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14
  app = Flask(__name__)
15
- app.config['UPLOAD_FOLDER'] = './uploads/'
16
- app.config['ALLOWED_EXTENSIONS'] = {'zip', 'xlsx'}
17
- app.config['RESULTS_FOLDER'] = './results/'
18
-
19
- classifier = YOLO("./models/classification.pt")
20
- detector = YOLO("./models/detection.pt")
21
- reader = Reader(['en'])
22
-
23
- def process_image(image_path):
24
- if classifier.predict(image_path)[0].probs.numpy().top1 == 0:
25
- fields = detector(image_path)
26
- image = cv2.imread(image_path)
27
- extracted_data = {}
28
- for field in fields[0].boxes.data.tolist():
29
- x1, y1, x2, y2, confidence, class_id = map(int, field[:6])
30
- field_class = detector.names[class_id]
31
- cropped_roi = image[y1:y2, x1:x2]
32
- gray_roi = cv2.cvtColor(cropped_roi, cv2.COLOR_BGR2GRAY)
33
- text = reader.readtext(gray_roi, detail=0)
34
- extracted_data[field_class] = ' '.join(text)
35
- return extracted_data
 
 
 
 
 
36
  return None
37
 
38
  # Helper Functions
@@ -241,58 +271,118 @@ def contact():
241
 
242
  @app.route('/upload', methods=['POST'])
243
  def upload_files():
244
- if 'zipfile' in request.files and 'excelfile' in request.files:
 
 
 
245
  zip_file = request.files['zipfile']
246
  excel_file = request.files['excelfile']
247
 
248
- # Save files
 
 
 
 
249
  zip_path = os.path.join(app.config['UPLOAD_FOLDER'], zip_file.filename)
250
  excel_path = os.path.join(app.config['UPLOAD_FOLDER'], excel_file.filename)
251
- zip_file.save(zip_path)
252
- excel_file.save(excel_path)
253
-
254
- # Unzip and process images
255
- with zipfile.ZipFile(zip_path, 'r') as zip_ref:
256
- zip_ref.extractall(app.config['UPLOAD_FOLDER'])
257
 
258
- image_paths = [os.path.join(app.config['UPLOAD_FOLDER'], f) for f in os.listdir(app.config['UPLOAD_FOLDER']) if f.endswith(('.jpg', '.png'))]
259
- processed_results = {}
260
-
261
- for image_path in image_paths:
262
- file_name = os.path.basename(image_path)
263
- key = file_name.split('.')[0][:3]
264
- if key not in processed_results: # Check if key already exists
265
- extracted_data = process_image(image_path)
266
- if extracted_data:
267
- processed_results[key] = extracted_data
268
-
269
- # Read Excel and compare data
270
- df = pd.read_excel(excel_path)
271
- df = df.astype('str')
272
- comparison_results = compare_data(df, processed_results)
273
- comparison_results['Accepted/Rejected'] = np.where(comparison_results['Final Remarks'] == 'All matched', 'Accepted', 'Rejected')
274
-
275
- # Save results to a new Excel file
276
- results_df = pd.DataFrame(comparison_results)
277
  os.makedirs(app.config['RESULTS_FOLDER'], exist_ok=True)
278
- results_file_path = os.path.join(app.config['RESULTS_FOLDER'], 'results.xlsx')
279
- results_df.to_excel(results_file_path, index=False)
280
-
281
- visualization_data = create_visualizations(comparison_results)
282
 
283
- create_database_and_table() # Ensure database and table exist
284
- save_results_to_database(comparison_results[
285
- ['SrNo', 'Document Type', 'Accepted/Rejected', 'Final Remarks']
286
- ].to_dict(orient='records'))
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
287
 
288
- return jsonify({"message": "Files processed successfully!",
289
- "results": comparison_results[
290
- ['SrNo', 'Document Type', 'Accepted/Rejected', 'Final Remarks']
291
- ].to_dict(orient='records'),
292
- "visualization_data": visualization_data})
293
-
294
- return jsonify({"error": "Both files are required."}), 400
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
295
 
296
  if __name__ == '__main__':
297
  # Configure HTTPS with self-signed certificate
298
- app.run()
 
11
  import json
12
  import sqlite3
13
 
14
+ # Ensure directories exist and are absolute
15
+ BASE_DIR = os.path.dirname(os.path.abspath(__file__))
16
+ UPLOAD_FOLDER = os.path.join(BASE_DIR, 'uploads')
17
+ RESULTS_FOLDER = os.path.join(BASE_DIR, 'results')
18
+ os.makedirs(UPLOAD_FOLDER, exist_ok=True)
19
+ os.makedirs(RESULTS_FOLDER, exist_ok=True)
20
+
21
+ # Load models with full path or from environment
22
+ MODEL_DIR = os.path.join(BASE_DIR, 'models')
23
+ try:
24
+ classifier = YOLO(os.path.join(MODEL_DIR, "classification.pt"))
25
+ detector = YOLO(os.path.join(MODEL_DIR, "detection.pt"))
26
+ except Exception as e:
27
+ print(f"Model loading error: {e}")
28
+ # Fallback mechanism or alternative model loading
29
+ classifier = None
30
+ detector = None
31
+
32
+ # Initialize EasyOCR with error handling
33
+ try:
34
+ reader = Reader(['en'])
35
+ except Exception as e:
36
+ print(f"EasyOCR initialization error: {e}")
37
+ reader = None
38
+
39
  app = Flask(__name__)
40
+ app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER
41
+ app.config['RESULTS_FOLDER'] = RESULTS_FOLDER
42
+
43
+ def safe_process_image(image_path):
44
+ """Safe image processing with extensive error handling"""
45
+ try:
46
+ if not classifier or not detector or not reader:
47
+ raise ValueError("Models not properly initialized")
48
+
49
+ classification_result = classifier.predict(image_path)[0]
50
+ if classification_result.probs.numpy().top1 == 0:
51
+ fields = detector(image_path)
52
+ image = cv2.imread(image_path)
53
+ extracted_data = {}
54
+
55
+ for field in fields[0].boxes.data.tolist():
56
+ x1, y1, x2, y2, confidence, class_id = map(int, field[:6])
57
+ field_class = detector.names[class_id]
58
+ cropped_roi = image[y1:y2, x1:x2]
59
+ gray_roi = cv2.cvtColor(cropped_roi, cv2.COLOR_BGR2GRAY)
60
+ text = reader.readtext(gray_roi, detail=0)
61
+ extracted_data[field_class] = ' '.join(text)
62
+
63
+ return extracted_data
64
+ except Exception as e:
65
+ print(f"Image processing error: {e}")
66
  return None
67
 
68
  # Helper Functions
 
271
 
272
  @app.route('/upload', methods=['POST'])
273
  def upload_files():
274
+ try:
275
+ if 'zipfile' not in request.files or 'excelfile' not in request.files:
276
+ return jsonify({"error": "Both files are required."}), 400
277
+
278
  zip_file = request.files['zipfile']
279
  excel_file = request.files['excelfile']
280
 
281
+ # Validate file types
282
+ if not zip_file.filename.endswith('.zip') or not excel_file.filename.endswith('.xlsx'):
283
+ return jsonify({"error": "Invalid file formats. Need .zip and .xlsx files."}), 400
284
+
285
+ # Create absolute paths
286
  zip_path = os.path.join(app.config['UPLOAD_FOLDER'], zip_file.filename)
287
  excel_path = os.path.join(app.config['UPLOAD_FOLDER'], excel_file.filename)
 
 
 
 
 
 
288
 
289
+ # Ensure directories exist
290
+ os.makedirs(app.config['UPLOAD_FOLDER'], exist_ok=True)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
291
  os.makedirs(app.config['RESULTS_FOLDER'], exist_ok=True)
 
 
 
 
292
 
293
+ # Save files with error handling
294
+ try:
295
+ zip_file.save(zip_path)
296
+ excel_file.save(excel_path)
297
+ except Exception as e:
298
+ return jsonify({"error": f"File save error: {str(e)}"}), 500
299
+
300
+ # Extract zip with error handling
301
+ try:
302
+ with zipfile.ZipFile(zip_path, 'r') as zip_ref:
303
+ zip_ref.extractall(app.config['UPLOAD_FOLDER'])
304
+ except zipfile.BadZipFile:
305
+ return jsonify({"error": "Invalid or corrupted zip file"}), 400
306
+
307
+ # Process images with memory management
308
+ image_paths = [os.path.join(app.config['UPLOAD_FOLDER'], f)
309
+ for f in os.listdir(app.config['UPLOAD_FOLDER'])
310
+ if f.lower().endswith(('.jpg', '.jpeg', '.png'))]
311
+
312
+ if not image_paths:
313
+ return jsonify({"error": "No valid images found in zip file"}), 400
314
 
315
+ processed_results = {}
316
+ for image_path in image_paths:
317
+ try:
318
+ file_name = os.path.basename(image_path)
319
+ key = file_name.split('.')[0][:3]
320
+ if key not in processed_results:
321
+ extracted_data = process_image(image_path)
322
+ if extracted_data:
323
+ processed_results[key] = extracted_data
324
+ # Clean up processed image
325
+ if os.path.exists(image_path):
326
+ os.remove(image_path)
327
+ except Exception as e:
328
+ print(f"Error processing image {image_path}: {str(e)}")
329
+ continue
330
+
331
+ # Process Excel with error handling
332
+ try:
333
+ df = pd.read_excel(excel_path)
334
+ df = df.astype(str)
335
+ comparison_results = compare_data(df, processed_results)
336
+ comparison_results['Accepted/Rejected'] = np.where(
337
+ comparison_results['Final Remarks'] == 'All matched',
338
+ 'Accepted',
339
+ 'Rejected'
340
+ )
341
+
342
+ # Save results
343
+ results_df = pd.DataFrame(comparison_results)
344
+ results_file_path = os.path.join(app.config['RESULTS_FOLDER'], 'results.xlsx')
345
+ results_df.to_excel(results_file_path, index=False)
346
+
347
+ visualization_data = create_visualizations(comparison_results)
348
+
349
+ # Database operations with error handling
350
+ try:
351
+ create_database_and_table()
352
+ save_results_to_database(comparison_results[
353
+ ['SrNo', 'Document Type', 'Accepted/Rejected', 'Final Remarks']
354
+ ].to_dict(orient='records'))
355
+ except Exception as e:
356
+ print(f"Database operation error: {str(e)}")
357
+
358
+ # Clean up input files
359
+ os.remove(zip_path)
360
+ os.remove(excel_path)
361
+
362
+ return jsonify({
363
+ "message": "Files processed successfully!",
364
+ "results": comparison_results[
365
+ ['SrNo', 'Document Type', 'Accepted/Rejected', 'Final Remarks']
366
+ ].to_dict(orient='records'),
367
+ "visualization_data": visualization_data
368
+ })
369
+
370
+ except Exception as e:
371
+ return jsonify({"error": f"Excel processing error: {str(e)}"}), 500
372
+
373
+ except Exception as e:
374
+ return jsonify({"error": f"General processing error: {str(e)}"}), 500
375
+
376
+ finally:
377
+ # Cleanup any remaining temporary files
378
+ for f in os.listdir(app.config['UPLOAD_FOLDER']):
379
+ try:
380
+ file_path = os.path.join(app.config['UPLOAD_FOLDER'], f)
381
+ if os.path.isfile(file_path):
382
+ os.remove(file_path)
383
+ except Exception as e:
384
+ print(f"Cleanup error: {str(e)}")
385
 
386
  if __name__ == '__main__':
387
  # Configure HTTPS with self-signed certificate
388
+ app.run(host='0.0.0.0', port=7860)