diff --git a/mobile/apps/photos/lib/db/ml/db.dart b/mobile/apps/photos/lib/db/ml/db.dart index 851e349d00..5ab5d28c8b 100644 --- a/mobile/apps/photos/lib/db/ml/db.dart +++ b/mobile/apps/photos/lib/db/ml/db.dart @@ -360,6 +360,10 @@ class MLDataDB with SqlDbBase implements IMLDataDB { } return mapRowToFace(faceMaps.first); } + } else if (clusterID == null) { + _logger.severe( + "Didn't find any faces for personID $personID in `getCoverFaceForPerson`.", + ); } if (clusterID != null) { const String queryFaceID = ''' @@ -380,11 +384,19 @@ class MLDataDB with SqlDbBase implements IMLDataDB { return face; } } + } else { + _logger.severe( + "Didn't find any faces for clusterID $clusterID in `getCoverFaceForPerson`. faces: $faces", + ); } } if (personID == null && clusterID == null) { + _logger.severe("personID and clusterID cannot be null both"); throw Exception("personID and clusterID cannot be null"); } + _logger.severe( + "Something went wrong finding a face from `getCoverFaceForPerson` (personID: $personID, clusterID: $clusterID)", + ); return null; } diff --git a/mobile/apps/photos/lib/services/machine_learning/face_thumbnail_generator.dart b/mobile/apps/photos/lib/services/machine_learning/face_thumbnail_generator.dart index b61763c782..6e09744cff 100644 --- a/mobile/apps/photos/lib/services/machine_learning/face_thumbnail_generator.dart +++ b/mobile/apps/photos/lib/services/machine_learning/face_thumbnail_generator.dart @@ -35,20 +35,30 @@ class FaceThumbnailGenerator extends SuperIsolate { String imagePath, List faceBoxes, ) async { - final List> faceBoxesJson = - faceBoxes.map((box) => box.toJson()).toList(); - final List faces = await runInIsolate( - IsolateOperation.generateFaceThumbnails, - { - 'imagePath': imagePath, - 'faceBoxesList': faceBoxesJson, - }, - ).then((value) => value.cast()); - final compressedFaces = - await compressFaceThumbnails({'listPngBytes': faces}); - _logger.fine( - "Compressed face thumbnails from sizes ${faces.map((e) => e.length / 1024).toList()} to ${compressedFaces.map((e) => e.length / 1024).toList()} kilobytes", - ); - return compressedFaces; + try { + _logger.info( + "Generating face thumbnails for ${faceBoxes.length} face boxes in $imagePath", + ); + final List> faceBoxesJson = + faceBoxes.map((box) => box.toJson()).toList(); + final List faces = await runInIsolate( + IsolateOperation.generateFaceThumbnails, + { + 'imagePath': imagePath, + 'faceBoxesList': faceBoxesJson, + }, + ).then((value) => value.cast()); + _logger.info("Generated face thumbnails"); + final compressedFaces = + await compressFaceThumbnails({'listPngBytes': faces}); + _logger.fine( + "Compressed face thumbnails from sizes ${faces.map((e) => e.length / 1024).toList()} to ${compressedFaces.map((e) => e.length / 1024).toList()} kilobytes", + ); + return compressedFaces; + } catch (e, s) { + _logger.severe("Failed to generate face thumbnails", e, s); + + rethrow; + } } } diff --git a/mobile/apps/photos/lib/ui/viewer/people/person_face_widget.dart b/mobile/apps/photos/lib/ui/viewer/people/person_face_widget.dart index 8bd069f57e..0327c5853d 100644 --- a/mobile/apps/photos/lib/ui/viewer/people/person_face_widget.dart +++ b/mobile/apps/photos/lib/ui/viewer/people/person_face_widget.dart @@ -163,7 +163,7 @@ class _PersonFaceWidgetState extends State { } } if (fileForFaceCrop == null) { - _logger.warning( + _logger.severe( "No suitable file found for face crop for person: ${widget.personId} or cluster: ${widget.clusterID}", ); return null; @@ -176,7 +176,7 @@ class _PersonFaceWidgetState extends State { clusterID: widget.clusterID, ); if (face == null) { - debugPrint( + _logger.severe( "No cover face for person: ${widget.personId} or cluster ${widget.clusterID} and fileID ${fileForFaceCrop.uploadedFileID!}", ); return null; @@ -188,7 +188,13 @@ class _PersonFaceWidgetState extends State { personOrClusterID: personOrClusterId, useTempCache: false, ); - return cropMap?[face.faceID]; + final result = cropMap?[face.faceID]; + if (result == null) { + _logger.severe( + "Null cover face crop for person: ${widget.personId} or cluster ${widget.clusterID} and fileID ${fileForFaceCrop.uploadedFileID!}", + ); + } + return result; } catch (e, s) { _logger.severe( "Error getting cover face for person: ${widget.personId} or cluster ${widget.clusterID}", diff --git a/mobile/apps/photos/lib/utils/face/face_thumbnail_cache.dart b/mobile/apps/photos/lib/utils/face/face_thumbnail_cache.dart index 117793173f..448eb7789a 100644 --- a/mobile/apps/photos/lib/utils/face/face_thumbnail_cache.dart +++ b/mobile/apps/photos/lib/utils/face/face_thumbnail_cache.dart @@ -129,7 +129,7 @@ Future?> getCachedFaceCrops( ); faceIdToCrop[face.faceID] = data; } else { - _logger.warning( + _logger.severe( "Cached face crop for faceID ${face.faceID} is empty, deleting file ${faceCropCacheFile.path}", ); await faceCropCacheFile.delete(); @@ -231,7 +231,7 @@ Future?> getCachedFaceCrops( s, ); } else { - _logger.info( + _logger.severe( "Stopped getting face crops for faceIDs: ${faces.map((face) => face.faceID).toList()} due to $e", ); } @@ -334,12 +334,14 @@ Future?> _getFaceCrops( if (useFullFile && file.fileType != FileType.video) { final File? ioFile = await getFile(file); if (ioFile == null) { + _logger.severe("Failed to get file for face crop generation"); return null; } imagePath = ioFile.path; } else { final thumbnail = await getThumbnailForUploadedFile(file); if (thumbnail == null) { + _logger.severe("Failed to get thumbnail for face crop generation"); return null; } imagePath = thumbnail.path; diff --git a/mobile/apps/photos/lib/utils/image_ml_util.dart b/mobile/apps/photos/lib/utils/image_ml_util.dart index 0ab1428fea..ab8b4a4e0f 100644 --- a/mobile/apps/photos/lib/utils/image_ml_util.dart +++ b/mobile/apps/photos/lib/utils/image_ml_util.dart @@ -575,7 +575,7 @@ Future> compressFaceThumbnails(Map args) async { } return await Future.wait(compressedBytesList); } catch (e, s) { - _logger.warning( + _logger.severe( 'Failed to compress face thumbnail, using original. Size: ${listPngBytes.map((e) => e.length).toList()} bytes', e, s,