Skip to content

Commit c4c4186

Browse files
committed
fix(analytics): improve error handling in data aggregation
- Use `firstOrNull` instead of accessing the first element directly - Add null safety checks for label and value in `_formatDataPoints` method - Implement null checks and logging for ranked list items
1 parent dec5fb3 commit c4c4186

File tree

1 file changed

+23
-11
lines changed

1 file changed

+23
-11
lines changed

lib/src/services/analytics/analytics_sync_service.dart

Lines changed: 23 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -375,7 +375,7 @@ class AnalyticsSyncService {
375375
},
376376
];
377377
final result = await _sourceRepository.aggregate(pipeline: pipeline);
378-
return result.first['total'] as num? ?? 0;
378+
return result.firstOrNull?['total'] as num? ?? 0;
379379
case 'database:topics:followers':
380380
final pipeline = [
381381
{
@@ -391,7 +391,7 @@ class AnalyticsSyncService {
391391
},
392392
];
393393
final result = await _topicRepository.aggregate(pipeline: pipeline);
394-
return result.first['total'] as num? ?? 0;
394+
return result.firstOrNull?['total'] as num? ?? 0;
395395
case 'database:reports:pending':
396396
return _reportRepository.count(
397397
filter: {'status': ModerationStatus.pendingReview.name},
@@ -431,15 +431,17 @@ class AnalyticsSyncService {
431431

432432
final results = await repo.aggregate(pipeline: pipeline);
433433
return results.map((e) {
434-
final label = e['label'].toString();
434+
final label = e['label']?.toString() ?? 'Unknown';
435+
final value = (e['value'] as num?) ?? 0;
436+
435437
final formattedLabel = label
436438
.split(' ')
437439
.map((word) {
438440
if (word.isEmpty) return '';
439441
return '${word[0].toUpperCase()}${word.substring(1)}';
440442
})
441443
.join(' ');
442-
return DataPoint(label: formattedLabel, value: e['value'] as num);
444+
return DataPoint(label: formattedLabel, value: value);
443445
}).toList();
444446
}
445447

@@ -467,13 +469,23 @@ class AnalyticsSyncService {
467469

468470
final results = await repo.aggregate(pipeline: pipeline);
469471
return results
470-
.map(
471-
(e) => RankedListItem(
472-
entityId: e['entityId'] as String,
473-
displayTitle: e['displayTitle'] as String,
474-
metricValue: e['metricValue'] as num,
475-
),
476-
)
472+
.map((e) {
473+
final entityId = e['entityId'] as String?;
474+
final displayTitle = e['displayTitle'] as String?;
475+
final metricValue = e['metricValue'] as num?;
476+
477+
if (entityId == null || displayTitle == null || metricValue == null) {
478+
_log.warning('Skipping ranked list item with missing data: $e');
479+
return null;
480+
}
481+
482+
return RankedListItem(
483+
entityId: entityId,
484+
displayTitle: displayTitle,
485+
metricValue: metricValue,
486+
);
487+
})
488+
.whereType<RankedListItem>()
477489
.toList();
478490
}
479491

0 commit comments

Comments
 (0)