fix_errors.py
8.5 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
#!/usr/bin/env python3
"""Fix the 10 remaining analysis errors."""
PATH = 'lib/pages/agent/agent_chat_page.dart'
with open(PATH, 'r') as f:
c = f.read()
# ===== Fix 1: Remove duplicate _maybeEnterReservationFlow (my version at line ~321) =====
# The original at line ~630 already exists. Replace my duplicate with nothing.
dup_maybe = '''
void _maybeEnterReservationFlow(String text) {
final ReservationImageParseResult parsed = ReservationImageParser.parse(text);
if (parsed.hasAny) _startReservationConversation(parsed);
}'''
if dup_maybe in c:
c = c.replace(dup_maybe, '', 1)
print("Removed duplicate _maybeEnterReservationFlow")
else:
print("WARNING: duplicate _maybeEnterReservationFlow not found")
# ===== Fix 2: Remove duplicate _normalizeReservationDate (my version) =====
# Find the one right after _mergeReservation (line ~130 area)
dup_norm = '''
ReservationImageParseResult _normalizeReservationDate(ReservationImageParseResult result) {
final DateTime now = DateTime.now();
String date = result.date.trim();
if (date.isEmpty) return result;
if (date == '今天' || date == '今日') {
date = '${now.year}-${now.month.toString().padLeft(2, '0')}-${now.day.toString().padLeft(2, '0')}';
} else if (date == '明天' || date == '明日') {
final DateTime t = now.add(const Duration(days: 1));
date = '${t.year}-${t.month.toString().padLeft(2, '0')}-${t.day.toString().padLeft(2, '0')}';
} else if (date == '后天') {
final DateTime t = now.add(const Duration(days: 2));
date = '${t.year}-${t.month.toString().padLeft(2, '0')}-${t.day.toString().padLeft(2, '0')}';
} else if (RegExp(r'^\\d{1,2}月\\d{1,2}日$').hasMatch(date)) {
final Match? m = RegExp(r'(\\d{1,2})月(\\d{1,2})日').firstMatch(date);
if (m != null) {
final int month = int.parse(m.group(1)!);
final int day = int.parse(m.group(2)!);
int year = now.year;
if (DateTime(year, month, day).isBefore(DateTime(now.year, now.month, now.day))) year++;
date = '$year-${month.toString().padLeft(2, '0')}-${day.toString().padLeft(2, '0')}';
}
}
return ReservationImageParseResult(name: result.name, sex: result.sex, phone: result.phone,
party: result.party, date: date, meal: result.meal, time: result.time,
table: result.table, remark: result.remark, rawText: result.rawText);
}'''
if dup_norm in c:
c = c.replace(dup_norm, '', 1)
print("Removed duplicate _normalizeReservationDate")
else:
print("WARNING: duplicate _normalizeReservationDate not found - trying simpler match")
# Try to find just the signature
idx = c.find(' ReservationImageParseResult _normalizeReservationDate(ReservationImageParseResult result) {')
idx2 = c.find(' ReservationImageParseResult _normalizeReservationDate(ReservationImageParseResult result) {', idx + 10)
if idx2 > idx:
print(f" Found second at {idx2}, removing...")
# Find end of this method
brace_count = 0
end_idx = idx2
for i in range(idx2, len(c)):
if c[i] == '{': brace_count += 1
elif c[i] == '}':
brace_count -= 1
if brace_count == 0:
end_idx = i + 1
break
c = c[:idx2] + c[end_idx:]
print(f" Removed {end_idx - idx2} chars")
# ===== Fix 3: Update original _maybeEnterReservationFlow to use conversation flow =====
old_maybe = ''' bool _maybeEnterReservationFlow(String text) {
final String trimmed = text.trim();
if (trimmed.isEmpty) return false;
final ReservationImageParseResult result =
ReservationImageParser.parse(trimmed);
if (!_isReservationText(result)) return false;
unawaited(_showReservationConfirm(_normalizeReservationDate(result)));
return true;
}'''
new_maybe = ''' bool _maybeEnterReservationFlow(String text) {
final String trimmed = text.trim();
if (trimmed.isEmpty) return false;
final ReservationImageParseResult result =
ReservationImageParser.parse(trimmed);
if (!_isReservationText(result)) return false;
_startReservationConversation(_normalizeReservationDate(result));
return true;
}'''
if old_maybe in c:
c = c.replace(old_maybe, new_maybe, 1)
print("Updated original _maybeEnterReservationFlow")
else:
print("WARNING: original _maybeEnterReservationFlow not found")
# ===== Fix 4: Add onSuggestion parameter to _MessageBubble =====
old_mb = '''class _MessageBubble extends StatelessWidget {
const _MessageBubble({required this.message, required this.themeColor});
final _ChatMessage message;
final Color themeColor;'''
new_mb = '''class _MessageBubble extends StatelessWidget {
const _MessageBubble({required this.message, required this.themeColor, this.onSuggestion});
final _ChatMessage message;
final Color themeColor;
final ValueChanged<String>? onSuggestion;'''
c = c.replace(old_mb, new_mb, 1)
print("Added onSuggestion to _MessageBubble")
# ===== Fix 5: Add reservationDraft to non-exhaustive switch statements =====
# Find the two switch(card.kind) blocks in _CardView._buildItems and _AgentCardDetailPage
# First, find them
for search in [' case _CardKind.orderList:', ' case _CardKind.dishRank:']:
idx = c.find(search)
while idx >= 0:
# Check if this is inside a switch that doesn't have reservationDraft yet
context = c[idx:idx+500]
if 'reservationDraft' not in context[:200]:
# This switch needs the case added
insert_pos = idx
# Find the 'default:' in this switch
default_idx = context.find(' default:')
if default_idx >= 0:
insert_pos = idx + default_idx
# Insert before default
c = c[:insert_pos] + " case _CardKind.reservationDraft:\n return Column(\n children: card.items.map((Map<String, dynamic> item) {\n return Padding(\n padding: const EdgeInsets.symmetric(vertical: 2),\n child: Row(\n crossAxisAlignment: CrossAxisAlignment.start,\n children: [\n Text('${item['label'] ?? ''}', style: const TextStyle(fontSize: 11, color: MyColours.color_999999)),\n const SizedBox(width: 10),\n Expanded(child: Text('${item['value'] ?? ''}', textAlign: TextAlign.right, style: const TextStyle(fontSize: 12, fontWeight: FontWeight.w600, color: Color(0xFF303030)))),\n ],\n ),\n );\n }).toList(),\n );\n" + c[insert_pos:]
print(f"Added reservationDraft case at offset {insert_pos}")
idx = c.find(search, idx + 1)
# ===== Fix 6: Pass onSuggestion from _send to _MessageBubble =====
# Find where _MessageBubble is instantiated
old_inst = ' return _MessageBubble(\n message: _messages[index],\n themeColor: themeColor,\n );'
new_inst = ' return _MessageBubble(\n message: _messages[index],\n themeColor: themeColor,\n onSuggestion: _send,\n );'
c = c.replace(old_inst, new_inst, 1)
print("Wired onSuggestion to _send")
# ===== Fix 7: _handleReservationClarification should handle all user messages with pending reservation =====
# Update _send to check and route to _handleReservationClarification
old_send = ''' if (_pendingReservation != null) {\n _handleReservationClarification(text);\n return;\n }'''
# Check if this routing already exists
if '_pendingReservation' in c and '_handleReservationClarification' not in c[:2000]:
print("Need to add routing for _handleReservationClarification")
# Find the _send method and add the check
send_idx = c.find(' void _send(String rawText) {')
if send_idx >= 0:
# Find the _maybeEnterReservationFlow check
maybe_idx = c.find('if (_maybeEnterReservationFlow(text))', send_idx)
if maybe_idx >= 0:
# Insert before it
insert_text = ''' if (_pendingReservation != null) {\n _handleReservationClarification(text);\n _inputController.clear();\n FocusScope.of(context).unfocus();\n return;\n }\n\n '''
c = c[:maybe_idx] + insert_text + c[maybe_idx:]
print("Added _handleReservationClarification routing to _send")
with open(PATH, 'w') as f:
f.write(c)
print(f"\nDone. Lines: {c.count(chr(10))}")