Source Code added

This commit is contained in:
Fr4nz D13trich 2026-02-02 15:06:40 +01:00
parent 800376eafd
commit 9efa9bc6dd
3912 changed files with 754770 additions and 2 deletions

View file

@ -0,0 +1,35 @@
import 'package:immich_mobile/entities/album.entity.dart';
class AvailableAlbum {
final Album album;
final int assetCount;
final DateTime? lastBackup;
const AvailableAlbum({required this.album, required this.assetCount, this.lastBackup});
AvailableAlbum copyWith({Album? album, int? assetCount, DateTime? lastBackup}) {
return AvailableAlbum(
album: album ?? this.album,
assetCount: assetCount ?? this.assetCount,
lastBackup: lastBackup ?? this.lastBackup,
);
}
String get name => album.name;
String get id => album.localId!;
bool get isAll => album.isAll;
@override
String toString() => 'AvailableAlbum(albumEntity: $album, lastBackup: $lastBackup)';
@override
bool operator ==(Object other) {
if (identical(this, other)) return true;
return other is AvailableAlbum && other.album == album;
}
@override
int get hashCode => album.hashCode;
}

View file

@ -0,0 +1,19 @@
import 'package:immich_mobile/entities/asset.entity.dart';
class BackupCandidate {
BackupCandidate({required this.asset, required this.albumNames});
Asset asset;
List<String> albumNames;
@override
int get hashCode => asset.hashCode;
@override
bool operator ==(Object other) {
if (other is! BackupCandidate) {
return false;
}
return asset == other.asset;
}
}

View file

@ -0,0 +1,180 @@
// ignore_for_file: public_member_api_docs, sort_constructors_first
import 'package:cancellation_token_http/http.dart';
import 'package:collection/collection.dart';
import 'package:immich_mobile/models/backup/backup_candidate.model.dart';
import 'package:immich_mobile/models/backup/available_album.model.dart';
import 'package:immich_mobile/models/backup/current_upload_asset.model.dart';
import 'package:immich_mobile/models/server_info/server_disk_info.model.dart';
enum BackUpProgressEnum { idle, inProgress, manualInProgress, inBackground, done }
class BackUpState {
// enum
final BackUpProgressEnum backupProgress;
final List<String> allAssetsInDatabase;
final double progressInPercentage;
final String progressInFileSize;
final double progressInFileSpeed;
final List<double> progressInFileSpeeds;
final DateTime progressInFileSpeedUpdateTime;
final int progressInFileSpeedUpdateSentBytes;
final double iCloudDownloadProgress;
final CancellationToken cancelToken;
final ServerDiskInfo serverInfo;
final bool autoBackup;
final bool backgroundBackup;
final bool backupRequireWifi;
final bool backupRequireCharging;
final int backupTriggerDelay;
/// All available albums on the device
final List<AvailableAlbum> availableAlbums;
final Set<AvailableAlbum> selectedBackupAlbums;
final Set<AvailableAlbum> excludedBackupAlbums;
/// Assets that are not overlapping in selected backup albums and excluded backup albums
final Set<BackupCandidate> allUniqueAssets;
/// All assets from the selected albums that have been backup
final Set<String> selectedAlbumsBackupAssetsIds;
// Current Backup Asset
final CurrentUploadAsset currentUploadAsset;
const BackUpState({
required this.backupProgress,
required this.allAssetsInDatabase,
required this.progressInPercentage,
required this.progressInFileSize,
required this.progressInFileSpeed,
required this.progressInFileSpeeds,
required this.progressInFileSpeedUpdateTime,
required this.progressInFileSpeedUpdateSentBytes,
required this.iCloudDownloadProgress,
required this.cancelToken,
required this.serverInfo,
required this.autoBackup,
required this.backgroundBackup,
required this.backupRequireWifi,
required this.backupRequireCharging,
required this.backupTriggerDelay,
required this.availableAlbums,
required this.selectedBackupAlbums,
required this.excludedBackupAlbums,
required this.allUniqueAssets,
required this.selectedAlbumsBackupAssetsIds,
required this.currentUploadAsset,
});
BackUpState copyWith({
BackUpProgressEnum? backupProgress,
List<String>? allAssetsInDatabase,
double? progressInPercentage,
String? progressInFileSize,
double? progressInFileSpeed,
List<double>? progressInFileSpeeds,
DateTime? progressInFileSpeedUpdateTime,
int? progressInFileSpeedUpdateSentBytes,
double? iCloudDownloadProgress,
CancellationToken? cancelToken,
ServerDiskInfo? serverInfo,
bool? autoBackup,
bool? backgroundBackup,
bool? backupRequireWifi,
bool? backupRequireCharging,
int? backupTriggerDelay,
List<AvailableAlbum>? availableAlbums,
Set<AvailableAlbum>? selectedBackupAlbums,
Set<AvailableAlbum>? excludedBackupAlbums,
Set<BackupCandidate>? allUniqueAssets,
Set<String>? selectedAlbumsBackupAssetsIds,
CurrentUploadAsset? currentUploadAsset,
}) {
return BackUpState(
backupProgress: backupProgress ?? this.backupProgress,
allAssetsInDatabase: allAssetsInDatabase ?? this.allAssetsInDatabase,
progressInPercentage: progressInPercentage ?? this.progressInPercentage,
progressInFileSize: progressInFileSize ?? this.progressInFileSize,
progressInFileSpeed: progressInFileSpeed ?? this.progressInFileSpeed,
progressInFileSpeeds: progressInFileSpeeds ?? this.progressInFileSpeeds,
progressInFileSpeedUpdateTime: progressInFileSpeedUpdateTime ?? this.progressInFileSpeedUpdateTime,
progressInFileSpeedUpdateSentBytes: progressInFileSpeedUpdateSentBytes ?? this.progressInFileSpeedUpdateSentBytes,
iCloudDownloadProgress: iCloudDownloadProgress ?? this.iCloudDownloadProgress,
cancelToken: cancelToken ?? this.cancelToken,
serverInfo: serverInfo ?? this.serverInfo,
autoBackup: autoBackup ?? this.autoBackup,
backgroundBackup: backgroundBackup ?? this.backgroundBackup,
backupRequireWifi: backupRequireWifi ?? this.backupRequireWifi,
backupRequireCharging: backupRequireCharging ?? this.backupRequireCharging,
backupTriggerDelay: backupTriggerDelay ?? this.backupTriggerDelay,
availableAlbums: availableAlbums ?? this.availableAlbums,
selectedBackupAlbums: selectedBackupAlbums ?? this.selectedBackupAlbums,
excludedBackupAlbums: excludedBackupAlbums ?? this.excludedBackupAlbums,
allUniqueAssets: allUniqueAssets ?? this.allUniqueAssets,
selectedAlbumsBackupAssetsIds: selectedAlbumsBackupAssetsIds ?? this.selectedAlbumsBackupAssetsIds,
currentUploadAsset: currentUploadAsset ?? this.currentUploadAsset,
);
}
@override
String toString() {
return 'BackUpState(backupProgress: $backupProgress, allAssetsInDatabase: $allAssetsInDatabase, progressInPercentage: $progressInPercentage, progressInFileSize: $progressInFileSize, progressInFileSpeed: $progressInFileSpeed, progressInFileSpeeds: $progressInFileSpeeds, progressInFileSpeedUpdateTime: $progressInFileSpeedUpdateTime, progressInFileSpeedUpdateSentBytes: $progressInFileSpeedUpdateSentBytes, iCloudDownloadProgress: $iCloudDownloadProgress, cancelToken: $cancelToken, serverInfo: $serverInfo, autoBackup: $autoBackup, backgroundBackup: $backgroundBackup, backupRequireWifi: $backupRequireWifi, backupRequireCharging: $backupRequireCharging, backupTriggerDelay: $backupTriggerDelay, availableAlbums: $availableAlbums, selectedBackupAlbums: $selectedBackupAlbums, excludedBackupAlbums: $excludedBackupAlbums, allUniqueAssets: $allUniqueAssets, selectedAlbumsBackupAssetsIds: $selectedAlbumsBackupAssetsIds, currentUploadAsset: $currentUploadAsset)';
}
@override
bool operator ==(covariant BackUpState other) {
if (identical(this, other)) return true;
final collectionEquals = const DeepCollectionEquality().equals;
return other.backupProgress == backupProgress &&
collectionEquals(other.allAssetsInDatabase, allAssetsInDatabase) &&
other.progressInPercentage == progressInPercentage &&
other.progressInFileSize == progressInFileSize &&
other.progressInFileSpeed == progressInFileSpeed &&
collectionEquals(other.progressInFileSpeeds, progressInFileSpeeds) &&
other.progressInFileSpeedUpdateTime == progressInFileSpeedUpdateTime &&
other.progressInFileSpeedUpdateSentBytes == progressInFileSpeedUpdateSentBytes &&
other.iCloudDownloadProgress == iCloudDownloadProgress &&
other.cancelToken == cancelToken &&
other.serverInfo == serverInfo &&
other.autoBackup == autoBackup &&
other.backgroundBackup == backgroundBackup &&
other.backupRequireWifi == backupRequireWifi &&
other.backupRequireCharging == backupRequireCharging &&
other.backupTriggerDelay == backupTriggerDelay &&
collectionEquals(other.availableAlbums, availableAlbums) &&
collectionEquals(other.selectedBackupAlbums, selectedBackupAlbums) &&
collectionEquals(other.excludedBackupAlbums, excludedBackupAlbums) &&
collectionEquals(other.allUniqueAssets, allUniqueAssets) &&
collectionEquals(other.selectedAlbumsBackupAssetsIds, selectedAlbumsBackupAssetsIds) &&
other.currentUploadAsset == currentUploadAsset;
}
@override
int get hashCode {
return backupProgress.hashCode ^
allAssetsInDatabase.hashCode ^
progressInPercentage.hashCode ^
progressInFileSize.hashCode ^
progressInFileSpeed.hashCode ^
progressInFileSpeeds.hashCode ^
progressInFileSpeedUpdateTime.hashCode ^
progressInFileSpeedUpdateSentBytes.hashCode ^
iCloudDownloadProgress.hashCode ^
cancelToken.hashCode ^
serverInfo.hashCode ^
autoBackup.hashCode ^
backgroundBackup.hashCode ^
backupRequireWifi.hashCode ^
backupRequireCharging.hashCode ^
backupTriggerDelay.hashCode ^
availableAlbums.hashCode ^
selectedBackupAlbums.hashCode ^
excludedBackupAlbums.hashCode ^
allUniqueAssets.hashCode ^
selectedAlbumsBackupAssetsIds.hashCode ^
currentUploadAsset.hashCode;
}
}

View file

@ -0,0 +1,95 @@
// ignore_for_file: public_member_api_docs, sort_constructors_first
import 'dart:convert';
class CurrentUploadAsset {
final String id;
final DateTime fileCreatedAt;
final String fileName;
final String fileType;
final int? fileSize;
final bool? iCloudAsset;
const CurrentUploadAsset({
required this.id,
required this.fileCreatedAt,
required this.fileName,
required this.fileType,
this.fileSize,
this.iCloudAsset,
});
@pragma('vm:prefer-inline')
bool get isIcloudAsset => iCloudAsset != null && iCloudAsset!;
CurrentUploadAsset copyWith({
String? id,
DateTime? fileCreatedAt,
String? fileName,
String? fileType,
int? fileSize,
bool? iCloudAsset,
}) {
return CurrentUploadAsset(
id: id ?? this.id,
fileCreatedAt: fileCreatedAt ?? this.fileCreatedAt,
fileName: fileName ?? this.fileName,
fileType: fileType ?? this.fileType,
fileSize: fileSize ?? this.fileSize,
iCloudAsset: iCloudAsset ?? this.iCloudAsset,
);
}
Map<String, dynamic> toMap() {
return <String, dynamic>{
'id': id,
'fileCreatedAt': fileCreatedAt.millisecondsSinceEpoch,
'fileName': fileName,
'fileType': fileType,
'fileSize': fileSize,
'iCloudAsset': iCloudAsset,
};
}
factory CurrentUploadAsset.fromMap(Map<String, dynamic> map) {
return CurrentUploadAsset(
id: map['id'] as String,
fileCreatedAt: DateTime.fromMillisecondsSinceEpoch(map['fileCreatedAt'] as int),
fileName: map['fileName'] as String,
fileType: map['fileType'] as String,
fileSize: map['fileSize'] as int,
iCloudAsset: map['iCloudAsset'] != null ? map['iCloudAsset'] as bool : null,
);
}
String toJson() => json.encode(toMap());
factory CurrentUploadAsset.fromJson(String source) =>
CurrentUploadAsset.fromMap(json.decode(source) as Map<String, dynamic>);
@override
String toString() {
return 'CurrentUploadAsset(id: $id, fileCreatedAt: $fileCreatedAt, fileName: $fileName, fileType: $fileType, fileSize: $fileSize, iCloudAsset: $iCloudAsset)';
}
@override
bool operator ==(covariant CurrentUploadAsset other) {
if (identical(this, other)) return true;
return other.id == id &&
other.fileCreatedAt == fileCreatedAt &&
other.fileName == fileName &&
other.fileType == fileType &&
other.fileSize == fileSize &&
other.iCloudAsset == iCloudAsset;
}
@override
int get hashCode {
return id.hashCode ^
fileCreatedAt.hashCode ^
fileName.hashCode ^
fileType.hashCode ^
fileSize.hashCode ^
iCloudAsset.hashCode;
}
}

View file

@ -0,0 +1,65 @@
import 'package:immich_mobile/entities/asset.entity.dart';
class ErrorUploadAsset {
final String id;
final DateTime fileCreatedAt;
final String fileName;
final String fileType;
final Asset asset;
final String errorMessage;
const ErrorUploadAsset({
required this.id,
required this.fileCreatedAt,
required this.fileName,
required this.fileType,
required this.asset,
required this.errorMessage,
});
ErrorUploadAsset copyWith({
String? id,
DateTime? fileCreatedAt,
String? fileName,
String? fileType,
Asset? asset,
String? errorMessage,
}) {
return ErrorUploadAsset(
id: id ?? this.id,
fileCreatedAt: fileCreatedAt ?? this.fileCreatedAt,
fileName: fileName ?? this.fileName,
fileType: fileType ?? this.fileType,
asset: asset ?? this.asset,
errorMessage: errorMessage ?? this.errorMessage,
);
}
@override
String toString() {
return 'ErrorUploadAsset(id: $id, fileCreatedAt: $fileCreatedAt, fileName: $fileName, fileType: $fileType, asset: $asset, errorMessage: $errorMessage)';
}
@override
bool operator ==(Object other) {
if (identical(this, other)) return true;
return other is ErrorUploadAsset &&
other.id == id &&
other.fileCreatedAt == fileCreatedAt &&
other.fileName == fileName &&
other.fileType == fileType &&
other.asset == asset &&
other.errorMessage == errorMessage;
}
@override
int get hashCode {
return id.hashCode ^
fileCreatedAt.hashCode ^
fileName.hashCode ^
fileType.hashCode ^
asset.hashCode ^
errorMessage.hashCode;
}
}

View file

@ -0,0 +1,110 @@
import 'package:cancellation_token_http/http.dart';
import 'package:collection/collection.dart';
import 'package:immich_mobile/models/backup/current_upload_asset.model.dart';
class ManualUploadState {
final CancellationToken cancelToken;
// Current Backup Asset
final CurrentUploadAsset currentUploadAsset;
final int currentAssetIndex;
final bool showDetailedNotification;
/// Manual Upload Stats
final int totalAssetsToUpload;
final int successfulUploads;
final double progressInPercentage;
final String progressInFileSize;
final double progressInFileSpeed;
final List<double> progressInFileSpeeds;
final DateTime progressInFileSpeedUpdateTime;
final int progressInFileSpeedUpdateSentBytes;
const ManualUploadState({
required this.progressInPercentage,
required this.progressInFileSize,
required this.progressInFileSpeed,
required this.progressInFileSpeeds,
required this.progressInFileSpeedUpdateTime,
required this.progressInFileSpeedUpdateSentBytes,
required this.cancelToken,
required this.currentUploadAsset,
required this.totalAssetsToUpload,
required this.currentAssetIndex,
required this.successfulUploads,
required this.showDetailedNotification,
});
ManualUploadState copyWith({
double? progressInPercentage,
String? progressInFileSize,
double? progressInFileSpeed,
List<double>? progressInFileSpeeds,
DateTime? progressInFileSpeedUpdateTime,
int? progressInFileSpeedUpdateSentBytes,
CancellationToken? cancelToken,
CurrentUploadAsset? currentUploadAsset,
int? totalAssetsToUpload,
int? successfulUploads,
int? currentAssetIndex,
bool? showDetailedNotification,
}) {
return ManualUploadState(
progressInPercentage: progressInPercentage ?? this.progressInPercentage,
progressInFileSize: progressInFileSize ?? this.progressInFileSize,
progressInFileSpeed: progressInFileSpeed ?? this.progressInFileSpeed,
progressInFileSpeeds: progressInFileSpeeds ?? this.progressInFileSpeeds,
progressInFileSpeedUpdateTime: progressInFileSpeedUpdateTime ?? this.progressInFileSpeedUpdateTime,
progressInFileSpeedUpdateSentBytes: progressInFileSpeedUpdateSentBytes ?? this.progressInFileSpeedUpdateSentBytes,
cancelToken: cancelToken ?? this.cancelToken,
currentUploadAsset: currentUploadAsset ?? this.currentUploadAsset,
totalAssetsToUpload: totalAssetsToUpload ?? this.totalAssetsToUpload,
currentAssetIndex: currentAssetIndex ?? this.currentAssetIndex,
successfulUploads: successfulUploads ?? this.successfulUploads,
showDetailedNotification: showDetailedNotification ?? this.showDetailedNotification,
);
}
@override
String toString() {
return 'ManualUploadState(progressInPercentage: $progressInPercentage, progressInFileSize: $progressInFileSize, progressInFileSpeed: $progressInFileSpeed, progressInFileSpeeds: $progressInFileSpeeds, progressInFileSpeedUpdateTime: $progressInFileSpeedUpdateTime, progressInFileSpeedUpdateSentBytes: $progressInFileSpeedUpdateSentBytes, cancelToken: $cancelToken, currentUploadAsset: $currentUploadAsset, totalAssetsToUpload: $totalAssetsToUpload, successfulUploads: $successfulUploads, currentAssetIndex: $currentAssetIndex, showDetailedNotification: $showDetailedNotification)';
}
@override
bool operator ==(Object other) {
if (identical(this, other)) return true;
final collectionEquals = const DeepCollectionEquality().equals;
return other is ManualUploadState &&
other.progressInPercentage == progressInPercentage &&
other.progressInFileSize == progressInFileSize &&
other.progressInFileSpeed == progressInFileSpeed &&
collectionEquals(other.progressInFileSpeeds, progressInFileSpeeds) &&
other.progressInFileSpeedUpdateTime == progressInFileSpeedUpdateTime &&
other.progressInFileSpeedUpdateSentBytes == progressInFileSpeedUpdateSentBytes &&
other.cancelToken == cancelToken &&
other.currentUploadAsset == currentUploadAsset &&
other.totalAssetsToUpload == totalAssetsToUpload &&
other.currentAssetIndex == currentAssetIndex &&
other.successfulUploads == successfulUploads &&
other.showDetailedNotification == showDetailedNotification;
}
@override
int get hashCode {
return progressInPercentage.hashCode ^
progressInFileSize.hashCode ^
progressInFileSpeed.hashCode ^
progressInFileSpeeds.hashCode ^
progressInFileSpeedUpdateTime.hashCode ^
progressInFileSpeedUpdateSentBytes.hashCode ^
cancelToken.hashCode ^
currentUploadAsset.hashCode ^
totalAssetsToUpload.hashCode ^
currentAssetIndex.hashCode ^
successfulUploads.hashCode ^
showDetailedNotification.hashCode;
}
}

View file

@ -0,0 +1,31 @@
import 'package:immich_mobile/models/backup/backup_candidate.model.dart';
class SuccessUploadAsset {
final BackupCandidate candidate;
final String remoteAssetId;
final bool isDuplicate;
const SuccessUploadAsset({required this.candidate, required this.remoteAssetId, required this.isDuplicate});
SuccessUploadAsset copyWith({BackupCandidate? candidate, String? remoteAssetId, bool? isDuplicate}) {
return SuccessUploadAsset(
candidate: candidate ?? this.candidate,
remoteAssetId: remoteAssetId ?? this.remoteAssetId,
isDuplicate: isDuplicate ?? this.isDuplicate,
);
}
@override
String toString() =>
'SuccessUploadAsset(asset: $candidate, remoteAssetId: $remoteAssetId, isDuplicate: $isDuplicate)';
@override
bool operator ==(covariant SuccessUploadAsset other) {
if (identical(this, other)) return true;
return other.candidate == candidate && other.remoteAssetId == remoteAssetId && other.isDuplicate == isDuplicate;
}
@override
int get hashCode => candidate.hashCode ^ remoteAssetId.hashCode ^ isDuplicate.hashCode;
}