Refactor
This commit is contained in:
@@ -134,86 +134,7 @@ class EnteFile {
|
||||
return AssetEntity.fromId(localID!);
|
||||
}
|
||||
|
||||
Future<Map<String, dynamic>> getMetadataForUpload(
|
||||
MediaUploadData mediaUploadData,
|
||||
ParsedExifDateTime? exifTime,
|
||||
) async {
|
||||
final asset = await getAsset;
|
||||
// asset can be null for files shared to app
|
||||
if (asset != null) {
|
||||
if (asset.type == AssetType.video) {
|
||||
duration = asset.duration;
|
||||
}
|
||||
}
|
||||
bool hasExifTime = false;
|
||||
if (exifTime != null && exifTime.time != null) {
|
||||
hasExifTime = true;
|
||||
creationTime = exifTime.time!.microsecondsSinceEpoch;
|
||||
}
|
||||
if (mediaUploadData.exifData != null) {
|
||||
mediaUploadData.isPanorama =
|
||||
checkPanoramaFromEXIF(null, mediaUploadData.exifData);
|
||||
}
|
||||
if (mediaUploadData.isPanorama != true &&
|
||||
fileType == FileType.image &&
|
||||
mediaUploadData.sourceFile != null) {
|
||||
try {
|
||||
final xmpData = await getXmp(mediaUploadData.sourceFile!);
|
||||
mediaUploadData.isPanorama = checkPanoramaFromXMP(xmpData);
|
||||
} catch (_) {}
|
||||
mediaUploadData.isPanorama ??= false;
|
||||
}
|
||||
|
||||
// Try to get the timestamp from fileName. In case of iOS, file names are
|
||||
// generic IMG_XXXX, so only parse it on Android devices
|
||||
if (!hasExifTime && Platform.isAndroid && title != null) {
|
||||
final timeFromFileName = parseDateTimeFromName(title!);
|
||||
if (timeFromFileName != null) {
|
||||
// only use timeFromFileName if the existing creationTime and
|
||||
// timeFromFilename belongs to different date.
|
||||
// This is done because many times the fileTimeStamp will only give us
|
||||
// the date, not time value but the photo_manager's creation time will
|
||||
// contain the time.
|
||||
final bool useFileTimeStamp = creationTime == null ||
|
||||
!areFromSameDay(
|
||||
creationTime!,
|
||||
timeFromFileName.microsecondsSinceEpoch,
|
||||
);
|
||||
if (useFileTimeStamp) {
|
||||
creationTime = timeFromFileName.microsecondsSinceEpoch;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final metadata = <String, dynamic>{};
|
||||
metadata["localID"] = asset?.id;
|
||||
final String? hashValue = mediaUploadData.hashData?.fileHash;
|
||||
if (hashValue != null) {
|
||||
metadata["hash"] = hashValue;
|
||||
}
|
||||
if (asset != null) {
|
||||
metadata["subType"] = asset.subtype;
|
||||
}
|
||||
metadata["version"] = kCurrentMetadataVersion;
|
||||
|
||||
metadata["title"] = title;
|
||||
metadata["deviceFolder"] = deviceFolder;
|
||||
metadata["creationTime"] = creationTime;
|
||||
metadata["modificationTime"] = modificationTime;
|
||||
metadata["fileType"] = fileType.index;
|
||||
if (location != null &&
|
||||
location!.latitude != null &&
|
||||
location!.longitude != null) {
|
||||
metadata["latitude"] = location!.latitude;
|
||||
metadata["longitude"] = location!.longitude;
|
||||
}
|
||||
|
||||
if (duration != null) {
|
||||
metadata["duration"] = duration;
|
||||
}
|
||||
|
||||
return metadata;
|
||||
}
|
||||
|
||||
|
||||
String get downloadUrl =>
|
||||
FileUrl.getUrl(uploadedFileID!, FileUrlType.download);
|
||||
|
||||
@@ -8,7 +8,6 @@ import "package:logging/logging.dart";
|
||||
import "package:motion_photos/motion_photos.dart";
|
||||
import "package:photos/extensions/stop_watch.dart";
|
||||
import "package:photos/models/ffmpeg/ffprobe_props.dart";
|
||||
import "package:photos/models/file/file.dart";
|
||||
import "package:photos/models/local/local_metadata.dart";
|
||||
import "package:photos/models/location/location.dart";
|
||||
import "package:photos/services/local/asset_entity.service.dart";
|
||||
@@ -28,7 +27,7 @@ class LocalMetadataService {
|
||||
final latLng = await asset.latlngAsync();
|
||||
Location location =
|
||||
Location(latitude: latLng.latitude, longitude: latLng.longitude);
|
||||
final int size = await sourceFile.length();
|
||||
final int size = sourceFile.lengthSync();
|
||||
final Map<String, IfdTag>? exifData = await tryExifFromFile(sourceFile);
|
||||
final int? mviIndex = asset.type != AssetType.image
|
||||
? null
|
||||
|
||||
@@ -705,17 +705,12 @@ class FileUploader {
|
||||
null,
|
||||
mediaUploadData.exifData,
|
||||
);
|
||||
final metadata =
|
||||
await file.getMetadataForUpload(mediaUploadData, exifTime);
|
||||
final Map<String, dynamic> metadata =
|
||||
await getMetadata(mediaUploadData, exifTime, file);
|
||||
final Map<String, dynamic> pubMetadata =
|
||||
_buildPublicMagicData(mediaUploadData, exifTime, file.rAsset);
|
||||
MetadataRequest? pubMetadataRequest;
|
||||
|
||||
final fileDecryptionHeader =
|
||||
CryptoUtil.bin2base64(fileEncryptResult.header!);
|
||||
final thumbnailDecryptionHeader =
|
||||
CryptoUtil.bin2base64(thumbEncResult.header!);
|
||||
|
||||
final encryptedMetadataResult = await CryptoUtil.encryptChaCha(
|
||||
utf8.encode(jsonEncode(metadata)),
|
||||
fileEncryptResult.key!,
|
||||
@@ -733,6 +728,10 @@ class FileUploader {
|
||||
fileEncryptResult.key!,
|
||||
);
|
||||
}
|
||||
final fileDecryptionHeader =
|
||||
CryptoUtil.bin2base64(fileEncryptResult.header!);
|
||||
final thumbnailDecryptionHeader =
|
||||
CryptoUtil.bin2base64(thumbEncResult.header!);
|
||||
if (SyncService.instance.shouldStopSync()) {
|
||||
throw SyncStopRequestedError();
|
||||
}
|
||||
|
||||
@@ -26,6 +26,8 @@ import "package:photos/services/local/import/local_import.dart";
|
||||
import "package:photos/services/local/livephoto.dart";
|
||||
import "package:photos/services/local/shared_assert.service.dart";
|
||||
import "package:photos/utils/exif_util.dart";
|
||||
import "package:photos/utils/panorama_util.dart";
|
||||
import "package:photos/utils/standalone/date_time.dart";
|
||||
import "package:photos/utils/standalone/decode_image.dart";
|
||||
import 'package:video_thumbnail/video_thumbnail.dart';
|
||||
|
||||
@@ -80,6 +82,7 @@ Future<MediaUploadData> _getMediaUploadDataFromAssetFile(
|
||||
_logger.severe('error while detecthing motion photo start index', e);
|
||||
}
|
||||
}
|
||||
|
||||
fileHash = CryptoUtil.bin2base64(await CryptoUtil.getHash(sourceFile));
|
||||
if (file.fileType == FileType.livePhoto && Platform.isIOS) {
|
||||
final (videoUrl, videoHash) =
|
||||
@@ -124,8 +127,7 @@ Future<void> _decorateEnteFileData(
|
||||
Map<String, IfdTag>? exifData,
|
||||
) async {
|
||||
// h4ck to fetch location data if missing (thank you Android Q+) lazily only during uploads
|
||||
if (file.location == null ||
|
||||
(file.location!.latitude == 0 && file.location!.longitude == 0)) {
|
||||
if (!file.hasLocation) {
|
||||
final latLong = await asset.latlngAsync();
|
||||
file.location =
|
||||
Location(latitude: latLong.latitude, longitude: latLong.longitude);
|
||||
@@ -149,6 +151,95 @@ Future<void> _decorateEnteFileData(
|
||||
}
|
||||
}
|
||||
|
||||
Future<Map<String, dynamic>> getMetadata(
|
||||
MediaUploadData mediaUploadData,
|
||||
ParsedExifDateTime? exifTime,
|
||||
EnteFile file,
|
||||
) async {
|
||||
final AssetEntity? asset = await file.getAsset;
|
||||
int? duration;
|
||||
int? creationTime = file.creationTime;
|
||||
final FileType fileType = file.fileType;
|
||||
final String? title = file.title;
|
||||
final String? deviceFolder = file.deviceFolder;
|
||||
final int? modificationTime = file.modificationTime;
|
||||
final Location? location = file.location;
|
||||
// asset can be null for files shared to app
|
||||
if (asset != null) {
|
||||
if (asset.type == AssetType.video) {
|
||||
duration = asset.duration;
|
||||
}
|
||||
}
|
||||
bool hasExifTime = false;
|
||||
if (exifTime != null && exifTime.time != null) {
|
||||
hasExifTime = true;
|
||||
creationTime = exifTime.time!.microsecondsSinceEpoch;
|
||||
}
|
||||
if (mediaUploadData.exifData != null) {
|
||||
mediaUploadData.isPanorama =
|
||||
checkPanoramaFromEXIF(null, mediaUploadData.exifData);
|
||||
}
|
||||
if (mediaUploadData.isPanorama != true &&
|
||||
fileType == FileType.image &&
|
||||
mediaUploadData.sourceFile != null) {
|
||||
try {
|
||||
final xmpData = await getXmp(mediaUploadData.sourceFile!);
|
||||
mediaUploadData.isPanorama = checkPanoramaFromXMP(xmpData);
|
||||
} catch (_) {}
|
||||
mediaUploadData.isPanorama ??= false;
|
||||
}
|
||||
|
||||
// Try to get the timestamp from fileName. In case of iOS, file names are
|
||||
// generic IMG_XXXX, so only parse it on Android devices
|
||||
if (!hasExifTime && Platform.isAndroid && title != null) {
|
||||
final timeFromFileName = parseDateTimeFromName(title);
|
||||
if (timeFromFileName != null) {
|
||||
// only use timeFromFileName if the existing creationTime and
|
||||
// timeFromFilename belongs to different date.
|
||||
// This is done because many times the fileTimeStamp will only give us
|
||||
// the date, not time value but the photo_manager's creation time will
|
||||
// contain the time.
|
||||
final bool useFileTimeStamp = creationTime == null ||
|
||||
!areFromSameDay(
|
||||
creationTime!,
|
||||
timeFromFileName.microsecondsSinceEpoch,
|
||||
);
|
||||
if (useFileTimeStamp) {
|
||||
creationTime = timeFromFileName.microsecondsSinceEpoch;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final metadata = <String, dynamic>{};
|
||||
metadata["localID"] = asset?.id;
|
||||
final String? hashValue = mediaUploadData.hashData?.fileHash;
|
||||
if (hashValue != null) {
|
||||
metadata["hash"] = hashValue;
|
||||
}
|
||||
if (asset != null) {
|
||||
metadata["subType"] = asset.subtype;
|
||||
}
|
||||
metadata["version"] = EnteFile.kCurrentMetadataVersion;
|
||||
metadata["title"] = title;
|
||||
metadata["deviceFolder"] = deviceFolder;
|
||||
metadata["creationTime"] = creationTime;
|
||||
metadata["modificationTime"] = modificationTime;
|
||||
metadata["fileType"] = fileType.index;
|
||||
if (location != null &&
|
||||
location.latitude != null &&
|
||||
location.longitude != null &&
|
||||
(location.latitude != 0 && location.longitude != 0)) {
|
||||
metadata["latitude"] = location.latitude;
|
||||
metadata["longitude"] = location.longitude;
|
||||
}
|
||||
|
||||
if (duration != null) {
|
||||
metadata["duration"] = duration;
|
||||
}
|
||||
|
||||
return metadata;
|
||||
}
|
||||
|
||||
Future<MetadataRequest> getPubMetadataRequest(
|
||||
EnteFile file,
|
||||
Map<String, dynamic> jsonToUpdate,
|
||||
|
||||
Reference in New Issue
Block a user