fix(core): ignore benign SelectionContainer RangeError #101
Treat a RangeError raised from Flutter's selection delegate as a non-fatal framework error, like the concurrent-modification case. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
abdulmominsakib committed
Sep 28, 2026 at 09:44 UTC
007c8fa1935ff15862c3dc9e04e2e90c1a098738
2 files changed
+47
-3
lib/core/services/crash_report_service.dart
+12
-3
@@ -260,14 +260,23 @@ class CrashReportService {
260
/// - flutter/flutter#192081: Concurrent modification during iteration in
261
/// `MultiSelectableSelectionContainerDelegate.handleClearSelection` when
262
/// clearing selection across scrollable elements (e.g. Markdown code blocks).
263
+ /// - A stale-index `RangeError` in
264
+ /// `MultiSelectableSelectionContainerDelegate.getSelectionGeometry` when
265
+ /// selectables change while a selection edge is being updated.
266
static bool isBenignFrameworkError(Object error, [StackTrace? stack]) {
267
final errorStr = error.toString();
268
final stackStr = stack?.toString() ?? '';
269
+ final isSelectionStack =
270
+ stackStr.contains('MultiSelectableSelectionContainerDelegate') ||
271
+ stackStr.contains('selectable_region.dart') ||
272
+ stackStr.contains('_ScrollableSelectionContainerDelegate');
273
274
if (errorStr.contains('Concurrent modification during iteration') &&
268
- (stackStr.contains('MultiSelectableSelectionContainerDelegate') ||
269
- stackStr.contains('selectable_region.dart') ||
270
- stackStr.contains('_ScrollableSelectionContainerDelegate'))) {
275
+ isSelectionStack) {
276
+ return true;
277
+ }
278
+
279
+ if (error is RangeError && isSelectionStack) {
280
return true;
281
}
282
test/core/services/crash_report_service_test.dart
+35
@@ -179,4 +179,39 @@ void main() {
179
expect(service.currentCrash.value, isNull);
180
});
181
});
182
+
183
+ group('CrashReportService.isBenignFrameworkError', () {
184
+ final selectionStack = StackTrace.fromString(
185
+ '#0 List.[] (dart:core-patch/growable_array.dart)\n'
186
+ '#1 MultiSelectableSelectionContainerDelegate.getSelectionGeometry '
187
+ '(package:flutter/src/widgets/selectable_region.dart:2643)\n',
188
+ );
189
+
190
+ test('ignores selection RangeError (#101)', () {
191
+ final error = RangeError.index(3, [1, 2, 3], 'length');
192
+ expect(
193
+ CrashReportService.isBenignFrameworkError(error, selectionStack),
194
+ isTrue,
195
+ );
196
+ });
197
+
198
+ test('ignores selection concurrent modification (#99)', () {
199
+ final error = ConcurrentModificationError(<int>[]);
200
+ expect(
201
+ CrashReportService.isBenignFrameworkError(error, selectionStack),
202
+ isTrue,
203
+ );
204
+ });
205
+
206
+ test('reports RangeError outside selection code', () {
207
+ final error = RangeError.index(3, [1, 2, 3], 'length');
208
+ expect(
209
+ CrashReportService.isBenignFrameworkError(
210
+ error,
211
+ StackTrace.fromString('#0 main (package:localmind/main.dart)'),
212
+ ),
213
+ isFalse,
214
+ );
215
+ });
216
+ });
217
}