vargha commited on
Commit
4b09d70
·
1 Parent(s): 924f5e7

fixing batching for loading data

Browse files
assets/styles.css CHANGED
@@ -2,3 +2,181 @@
2
  align-items: center;
3
  padding: 12px 12px;
4
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
2
  align-items: center;
3
  padding: 12px 12px;
4
  }
5
+
6
+ /* Beautiful tqdm-style Progress Bar Styles */
7
+ .progress-container {
8
+ background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%);
9
+ border: 1px solid #dee2e6;
10
+ border-radius: 12px;
11
+ padding: 16px;
12
+ margin: 8px 0;
13
+ box-shadow: 0 2px 8px rgba(0,0,0,0.1);
14
+ font-family: 'SF Mono', Monaco, 'Cascadia Code', 'Roboto Mono', Consolas, 'Courier New', monospace;
15
+ }
16
+
17
+ .progress-header {
18
+ display: flex;
19
+ align-items: center;
20
+ gap: 8px;
21
+ margin-bottom: 12px;
22
+ font-size: 14px;
23
+ color: #495057;
24
+ }
25
+
26
+ .progress-icon {
27
+ font-size: 16px;
28
+ animation: pulse 2s infinite;
29
+ }
30
+
31
+ .progress-bar-container {
32
+ display: flex;
33
+ align-items: center;
34
+ gap: 12px;
35
+ margin-bottom: 10px;
36
+ }
37
+
38
+ .progress-percentage {
39
+ font-weight: bold;
40
+ font-size: 13px;
41
+ color: #495057;
42
+ min-width: 50px;
43
+ text-align: right;
44
+ }
45
+
46
+ .progress-bar {
47
+ flex: 1;
48
+ height: 8px;
49
+ background-color: #e9ecef;
50
+ border-radius: 4px;
51
+ overflow: hidden;
52
+ position: relative;
53
+ box-shadow: inset 0 1px 3px rgba(0,0,0,0.1);
54
+ }
55
+
56
+ .progress-fill {
57
+ height: 100%;
58
+ border-radius: 4px;
59
+ transition: width 0.3s ease;
60
+ position: relative;
61
+ overflow: hidden;
62
+ }
63
+
64
+ .progress-fill::after {
65
+ content: '';
66
+ position: absolute;
67
+ top: 0;
68
+ left: 0;
69
+ bottom: 0;
70
+ right: 0;
71
+ background-image: linear-gradient(
72
+ -45deg,
73
+ rgba(255, 255, 255, 0.2) 25%,
74
+ transparent 25%,
75
+ transparent 50%,
76
+ rgba(255, 255, 255, 0.2) 50%,
77
+ rgba(255, 255, 255, 0.2) 75%,
78
+ transparent 75%,
79
+ transparent
80
+ );
81
+ background-size: 20px 20px;
82
+ animation: progress-stripes 1s linear infinite;
83
+ }
84
+
85
+ @keyframes progress-stripes {
86
+ 0% { background-position: 0 0; }
87
+ 100% { background-position: 20px 0; }
88
+ }
89
+
90
+ .progress-bar-low .progress-fill {
91
+ background: linear-gradient(90deg, #dc3545, #e74c3c);
92
+ }
93
+
94
+ .progress-bar-medium-low .progress-fill {
95
+ background: linear-gradient(90deg, #ffc107, #f39c12);
96
+ }
97
+
98
+ .progress-bar-medium .progress-fill {
99
+ background: linear-gradient(90deg, #fd7e14, #e67e22);
100
+ }
101
+
102
+ .progress-bar-high .progress-fill {
103
+ background: linear-gradient(90deg, #28a745, #27ae60);
104
+ }
105
+
106
+ .progress-bar-complete .progress-fill {
107
+ background: linear-gradient(90deg, #20c997, #1abc9c);
108
+ animation: complete-pulse 1.5s ease-in-out infinite;
109
+ }
110
+
111
+ @keyframes complete-pulse {
112
+ 0%, 100% { opacity: 1; }
113
+ 50% { opacity: 0.8; }
114
+ }
115
+
116
+ .progress-stats {
117
+ font-weight: bold;
118
+ font-size: 13px;
119
+ color: #495057;
120
+ min-width: 60px;
121
+ }
122
+
123
+ .progress-details {
124
+ display: flex;
125
+ align-items: center;
126
+ gap: 8px;
127
+ font-size: 12px;
128
+ color: #6c757d;
129
+ margin-top: 8px;
130
+ }
131
+
132
+ .progress-details code {
133
+ background: #f8f9fa;
134
+ border: 1px solid #e9ecef;
135
+ border-radius: 4px;
136
+ padding: 2px 6px;
137
+ font-family: 'SF Mono', Monaco, 'Cascadia Code', 'Roboto Mono', Consolas, 'Courier New', monospace;
138
+ font-size: 11px;
139
+ letter-spacing: 0.5px;
140
+ color: #495057;
141
+ }
142
+
143
+ .remaining-items {
144
+ color: #6c757d;
145
+ font-style: italic;
146
+ }
147
+
148
+ @keyframes pulse {
149
+ 0%, 100% { transform: scale(1); }
150
+ 50% { transform: scale(1.1); }
151
+ }
152
+
153
+ /* Dark mode support */
154
+ @media (prefers-color-scheme: dark) {
155
+ .progress-container {
156
+ background: linear-gradient(135deg, #343a40 0%, #495057 100%);
157
+ border-color: #6c757d;
158
+ color: #f8f9fa;
159
+ }
160
+
161
+ .progress-header, .progress-percentage, .progress-stats {
162
+ color: #f8f9fa;
163
+ }
164
+
165
+ .progress-bar {
166
+ background-color: #495057;
167
+ }
168
+
169
+ .progress-details {
170
+ color: #adb5bd;
171
+ }
172
+
173
+ .progress-details code {
174
+ background: #495057;
175
+ border-color: #6c757d;
176
+ color: #f8f9fa;
177
+ }
178
+
179
+ .remaining-items {
180
+ color: #adb5bd;
181
+ }
182
+ }
components/review_dashboard_page.py CHANGED
@@ -481,15 +481,23 @@ class ReviewDashboardPage:
481
 
482
  def navigate_review_fn(items, current_idx, direction):
483
  if not items:
484
- return 0
485
  if direction == "next":
486
  new_idx = min(current_idx + 1, len(items) - 1)
487
- # Check if we're getting close to the end - load more items if needed
488
- if new_idx >= len(items) - 2 and len(items) % 5 == 0: # Near end and items is a multiple of initial batch size
489
- log.info(f"User is near end of loaded items ({new_idx}/{len(items)}), may need to load more items")
490
- return new_idx
 
491
  else: # prev
492
- return max(current_idx - 1, 0)
 
 
 
 
 
 
 
493
 
494
  def save_validation_fn(items, idx, session, approved: bool, rejection_reason: str = ""):
495
  if not items or idx >= len(items):
@@ -600,7 +608,7 @@ class ReviewDashboardPage:
600
  # gr.Warning(f"Invalid Data ID format: {target_data_id}")
601
  return current_idx
602
 
603
- def load_more_items_fn(items, session, current_batch_size=100):
604
  """Load more items when user needs them (pagination support)"""
605
  user_id = session.get("user_id")
606
  username = session.get("username")
@@ -625,44 +633,26 @@ class ReviewDashboardPage:
625
 
626
  # Load next batch starting from where we left off
627
  offset = len(items)
 
 
628
  query = db.query(
629
  Annotation,
630
  TTSData.filename,
631
- TTSData.sentence,
632
- Validation.validated,
633
- Validation.description
634
  ).join(
635
  TTSData, Annotation.tts_data_id == TTSData.id
636
- ).outerjoin(
637
- Validation,
638
- (Validation.annotation_id == Annotation.id) &
639
- (Validation.validator_id == user_id)
640
  ).filter(
641
  Annotation.annotator_id == target_annotator_obj.id
642
  ).order_by(Annotation.id).offset(offset).limit(current_batch_size)
643
 
644
  results = query.all()
645
 
646
- # Process new items same as before
647
  new_items = []
648
- for annotation, filename, sentence, validated, validation_description in results:
 
649
  is_deleted = not annotation.annotated_sentence or annotation.annotated_sentence.strip() == ""
650
-
651
- validation_status = "Not Reviewed"
652
- if validated is not None:
653
- if validated:
654
- validation_status = "Approved"
655
- else:
656
- validation_status = "Rejected"
657
- if validation_description:
658
- validation_status += f" ({validation_description})"
659
-
660
- if is_deleted:
661
- annotated_sentence_display = "[DELETED ANNOTATION]"
662
- if validation_status == "Not Reviewed":
663
- validation_status = "Not Reviewed (Deleted)"
664
- else:
665
- annotated_sentence_display = annotation.annotated_sentence
666
 
667
  new_items.append({
668
  "annotation_id": annotation.id,
@@ -672,7 +662,8 @@ class ReviewDashboardPage:
672
  "annotated_sentence": annotated_sentence_display,
673
  "is_deleted": is_deleted,
674
  "annotated_at": annotation.annotated_at.isoformat() if annotation.annotated_at else "",
675
- "validation_status": validation_status
 
676
  })
677
 
678
  # Combine with existing items
 
481
 
482
  def navigate_review_fn(items, current_idx, direction):
483
  if not items:
484
+ return 0, False
485
  if direction == "next":
486
  new_idx = min(current_idx + 1, len(items) - 1)
487
+ # Only load more items when user reaches the LAST item of a batch
488
+ should_load_more = (new_idx == len(items) - 1 and len(items) % 5 == 0)
489
+ if should_load_more:
490
+ log.info(f"User reached end of loaded items ({new_idx}/{len(items)}), will load more items")
491
+ return new_idx, should_load_more
492
  else: # prev
493
+ return max(current_idx - 1, 0), False
494
+
495
+ def conditional_load_more_fn(items, session, should_load_more):
496
+ """Load more items if needed, otherwise return existing items"""
497
+ if should_load_more:
498
+ log.info("Loading more items for navigation...")
499
+ return load_more_items_fn(items, session, current_batch_size=10) # Reduced from 50 to 10 items
500
+ return items
501
 
502
  def save_validation_fn(items, idx, session, approved: bool, rejection_reason: str = ""):
503
  if not items or idx >= len(items):
 
608
  # gr.Warning(f"Invalid Data ID format: {target_data_id}")
609
  return current_idx
610
 
611
+ def load_more_items_fn(items, session, current_batch_size=10):
612
  """Load more items when user needs them (pagination support)"""
613
  user_id = session.get("user_id")
614
  username = session.get("username")
 
633
 
634
  # Load next batch starting from where we left off
635
  offset = len(items)
636
+
637
+ # FAST LOADING: Use same strategy as initial load - simple query without complex JOINs
638
  query = db.query(
639
  Annotation,
640
  TTSData.filename,
641
+ TTSData.sentence
 
 
642
  ).join(
643
  TTSData, Annotation.tts_data_id == TTSData.id
 
 
 
 
644
  ).filter(
645
  Annotation.annotator_id == target_annotator_obj.id
646
  ).order_by(Annotation.id).offset(offset).limit(current_batch_size)
647
 
648
  results = query.all()
649
 
650
+ # Process new items with minimal data - validation status loaded on-demand
651
  new_items = []
652
+ for annotation, filename, sentence in results:
653
+ # Check if annotation is deleted (minimal processing)
654
  is_deleted = not annotation.annotated_sentence or annotation.annotated_sentence.strip() == ""
655
+ annotated_sentence_display = "[DELETED ANNOTATION]" if is_deleted else annotation.annotated_sentence
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
656
 
657
  new_items.append({
658
  "annotation_id": annotation.id,
 
662
  "annotated_sentence": annotated_sentence_display,
663
  "is_deleted": is_deleted,
664
  "annotated_at": annotation.annotated_at.isoformat() if annotation.annotated_at else "",
665
+ "validation_status": "Loading...", # Will be loaded on-demand
666
+ "validation_loaded": False # Track if validation status has been loaded
667
  })
668
 
669
  # Combine with existing items