refactor: rename db backup routes

This commit is contained in:
izzy
2025-12-03 11:47:48 +00:00
parent fe8eb85e37
commit a63b418507
14 changed files with 168 additions and 146 deletions

View File

@@ -133,11 +133,11 @@ Class | Method | HTTP request | Description
*AuthenticationApi* | [**unlockAuthSession**](doc//AuthenticationApi.md#unlockauthsession) | **POST** /auth/session/unlock | Unlock auth session *AuthenticationApi* | [**unlockAuthSession**](doc//AuthenticationApi.md#unlockauthsession) | **POST** /auth/session/unlock | Unlock auth session
*AuthenticationApi* | [**validateAccessToken**](doc//AuthenticationApi.md#validateaccesstoken) | **POST** /auth/validateToken | Validate access token *AuthenticationApi* | [**validateAccessToken**](doc//AuthenticationApi.md#validateaccesstoken) | **POST** /auth/validateToken | Validate access token
*AuthenticationAdminApi* | [**unlinkAllOAuthAccountsAdmin**](doc//AuthenticationAdminApi.md#unlinkalloauthaccountsadmin) | **POST** /admin/auth/unlink-all | Unlink all OAuth accounts *AuthenticationAdminApi* | [**unlinkAllOAuthAccountsAdmin**](doc//AuthenticationAdminApi.md#unlinkalloauthaccountsadmin) | **POST** /admin/auth/unlink-all | Unlink all OAuth accounts
*DatabaseBackupsAdminApi* | [**deleteBackup**](doc//DatabaseBackupsAdminApi.md#deletebackup) | **DELETE** /admin/database-backups/{filename} | Delete backup *DatabaseBackupsAdminApi* | [**deleteDatabaseBackup**](doc//DatabaseBackupsAdminApi.md#deletedatabasebackup) | **DELETE** /admin/database-backups/{filename} | Delete database backup
*DatabaseBackupsAdminApi* | [**downloadBackup**](doc//DatabaseBackupsAdminApi.md#downloadbackup) | **GET** /admin/database-backups/{filename} | Download backup *DatabaseBackupsAdminApi* | [**downloadDatabaseBackup**](doc//DatabaseBackupsAdminApi.md#downloaddatabasebackup) | **GET** /admin/database-backups/{filename} | Download database backup
*DatabaseBackupsAdminApi* | [**listBackups**](doc//DatabaseBackupsAdminApi.md#listbackups) | **GET** /admin/database-backups | List backups *DatabaseBackupsAdminApi* | [**listDatabaseBackups**](doc//DatabaseBackupsAdminApi.md#listdatabasebackups) | **GET** /admin/database-backups | List database backups
*DatabaseBackupsAdminApi* | [**startRestoreFlow**](doc//DatabaseBackupsAdminApi.md#startrestoreflow) | **POST** /admin/database-backups/start-restore | Start backup restore flow *DatabaseBackupsAdminApi* | [**startDatabaseRestoreFlow**](doc//DatabaseBackupsAdminApi.md#startdatabaserestoreflow) | **POST** /admin/database-backups/start-restore | Start database backup restore flow
*DatabaseBackupsAdminApi* | [**uploadBackup**](doc//DatabaseBackupsAdminApi.md#uploadbackup) | **POST** /admin/database-backups/upload | Upload database backup *DatabaseBackupsAdminApi* | [**uploadDatabaseBackup**](doc//DatabaseBackupsAdminApi.md#uploaddatabasebackup) | **POST** /admin/database-backups/upload | Upload database backup
*DeprecatedApi* | [**createPartnerDeprecated**](doc//DeprecatedApi.md#createpartnerdeprecated) | **POST** /partners/{id} | Create a partner *DeprecatedApi* | [**createPartnerDeprecated**](doc//DeprecatedApi.md#createpartnerdeprecated) | **POST** /partners/{id} | Create a partner
*DeprecatedApi* | [**getAllUserAssetsByDeviceId**](doc//DeprecatedApi.md#getalluserassetsbydeviceid) | **GET** /assets/device/{deviceId} | Retrieve assets by device ID *DeprecatedApi* | [**getAllUserAssetsByDeviceId**](doc//DeprecatedApi.md#getalluserassetsbydeviceid) | **GET** /assets/device/{deviceId} | Retrieve assets by device ID
*DeprecatedApi* | [**getDeltaSync**](doc//DeprecatedApi.md#getdeltasync) | **POST** /sync/delta-sync | Get delta sync for user *DeprecatedApi* | [**getDeltaSync**](doc//DeprecatedApi.md#getdeltasync) | **POST** /sync/delta-sync | Get delta sync for user
@@ -423,11 +423,11 @@ Class | Method | HTTP request | Description
- [MachineLearningAvailabilityChecksDto](doc//MachineLearningAvailabilityChecksDto.md) - [MachineLearningAvailabilityChecksDto](doc//MachineLearningAvailabilityChecksDto.md)
- [MaintenanceAction](doc//MaintenanceAction.md) - [MaintenanceAction](doc//MaintenanceAction.md)
- [MaintenanceAuthDto](doc//MaintenanceAuthDto.md) - [MaintenanceAuthDto](doc//MaintenanceAuthDto.md)
- [MaintenanceIntegrityResponseDto](doc//MaintenanceIntegrityResponseDto.md) - [MaintenanceDetectInstallResponseDto](doc//MaintenanceDetectInstallResponseDto.md)
- [MaintenanceDetectInstallStorageFolderDto](doc//MaintenanceDetectInstallStorageFolderDto.md)
- [MaintenanceListBackupsResponseDto](doc//MaintenanceListBackupsResponseDto.md) - [MaintenanceListBackupsResponseDto](doc//MaintenanceListBackupsResponseDto.md)
- [MaintenanceLoginDto](doc//MaintenanceLoginDto.md) - [MaintenanceLoginDto](doc//MaintenanceLoginDto.md)
- [MaintenanceStatusResponseDto](doc//MaintenanceStatusResponseDto.md) - [MaintenanceStatusResponseDto](doc//MaintenanceStatusResponseDto.md)
- [MaintenanceStorageFolderIntegrityDto](doc//MaintenanceStorageFolderIntegrityDto.md)
- [ManualJobName](doc//ManualJobName.md) - [ManualJobName](doc//ManualJobName.md)
- [MapMarkerResponseDto](doc//MapMarkerResponseDto.md) - [MapMarkerResponseDto](doc//MapMarkerResponseDto.md)
- [MapReverseGeocodeResponseDto](doc//MapReverseGeocodeResponseDto.md) - [MapReverseGeocodeResponseDto](doc//MapReverseGeocodeResponseDto.md)

View File

@@ -169,11 +169,11 @@ part 'model/logout_response_dto.dart';
part 'model/machine_learning_availability_checks_dto.dart'; part 'model/machine_learning_availability_checks_dto.dart';
part 'model/maintenance_action.dart'; part 'model/maintenance_action.dart';
part 'model/maintenance_auth_dto.dart'; part 'model/maintenance_auth_dto.dart';
part 'model/maintenance_integrity_response_dto.dart'; part 'model/maintenance_detect_install_response_dto.dart';
part 'model/maintenance_detect_install_storage_folder_dto.dart';
part 'model/maintenance_list_backups_response_dto.dart'; part 'model/maintenance_list_backups_response_dto.dart';
part 'model/maintenance_login_dto.dart'; part 'model/maintenance_login_dto.dart';
part 'model/maintenance_status_response_dto.dart'; part 'model/maintenance_status_response_dto.dart';
part 'model/maintenance_storage_folder_integrity_dto.dart';
part 'model/manual_job_name.dart'; part 'model/manual_job_name.dart';
part 'model/map_marker_response_dto.dart'; part 'model/map_marker_response_dto.dart';
part 'model/map_reverse_geocode_response_dto.dart'; part 'model/map_reverse_geocode_response_dto.dart';

View File

@@ -16,7 +16,7 @@ class DatabaseBackupsAdminApi {
final ApiClient apiClient; final ApiClient apiClient;
/// Delete backup /// Delete database backup
/// ///
/// Delete a backup by its filename /// Delete a backup by its filename
/// ///
@@ -25,7 +25,7 @@ class DatabaseBackupsAdminApi {
/// Parameters: /// Parameters:
/// ///
/// * [String] filename (required): /// * [String] filename (required):
Future<Response> deleteBackupWithHttpInfo(String filename,) async { Future<Response> deleteDatabaseBackupWithHttpInfo(String filename,) async {
// ignore: prefer_const_declarations // ignore: prefer_const_declarations
final apiPath = r'/admin/database-backups/{filename}' final apiPath = r'/admin/database-backups/{filename}'
.replaceAll('{filename}', filename); .replaceAll('{filename}', filename);
@@ -51,21 +51,21 @@ class DatabaseBackupsAdminApi {
); );
} }
/// Delete backup /// Delete database backup
/// ///
/// Delete a backup by its filename /// Delete a backup by its filename
/// ///
/// Parameters: /// Parameters:
/// ///
/// * [String] filename (required): /// * [String] filename (required):
Future<void> deleteBackup(String filename,) async { Future<void> deleteDatabaseBackup(String filename,) async {
final response = await deleteBackupWithHttpInfo(filename,); final response = await deleteDatabaseBackupWithHttpInfo(filename,);
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
} }
} }
/// Download backup /// Download database backup
/// ///
/// Downloads the database backup file /// Downloads the database backup file
/// ///
@@ -74,7 +74,7 @@ class DatabaseBackupsAdminApi {
/// Parameters: /// Parameters:
/// ///
/// * [String] filename (required): /// * [String] filename (required):
Future<Response> downloadBackupWithHttpInfo(String filename,) async { Future<Response> downloadDatabaseBackupWithHttpInfo(String filename,) async {
// ignore: prefer_const_declarations // ignore: prefer_const_declarations
final apiPath = r'/admin/database-backups/{filename}' final apiPath = r'/admin/database-backups/{filename}'
.replaceAll('{filename}', filename); .replaceAll('{filename}', filename);
@@ -100,15 +100,15 @@ class DatabaseBackupsAdminApi {
); );
} }
/// Download backup /// Download database backup
/// ///
/// Downloads the database backup file /// Downloads the database backup file
/// ///
/// Parameters: /// Parameters:
/// ///
/// * [String] filename (required): /// * [String] filename (required):
Future<MultipartFile?> downloadBackup(String filename,) async { Future<MultipartFile?> downloadDatabaseBackup(String filename,) async {
final response = await downloadBackupWithHttpInfo(filename,); final response = await downloadDatabaseBackupWithHttpInfo(filename,);
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
} }
@@ -122,12 +122,12 @@ class DatabaseBackupsAdminApi {
return null; return null;
} }
/// List backups /// List database backups
/// ///
/// Get the list of the successful and failed backups /// Get the list of the successful and failed backups
/// ///
/// Note: This method returns the HTTP [Response]. /// Note: This method returns the HTTP [Response].
Future<Response> listBackupsWithHttpInfo() async { Future<Response> listDatabaseBackupsWithHttpInfo() async {
// ignore: prefer_const_declarations // ignore: prefer_const_declarations
final apiPath = r'/admin/database-backups'; final apiPath = r'/admin/database-backups';
@@ -152,11 +152,11 @@ class DatabaseBackupsAdminApi {
); );
} }
/// List backups /// List database backups
/// ///
/// Get the list of the successful and failed backups /// Get the list of the successful and failed backups
Future<MaintenanceListBackupsResponseDto?> listBackups() async { Future<MaintenanceListBackupsResponseDto?> listDatabaseBackups() async {
final response = await listBackupsWithHttpInfo(); final response = await listDatabaseBackupsWithHttpInfo();
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
} }
@@ -170,12 +170,12 @@ class DatabaseBackupsAdminApi {
return null; return null;
} }
/// Start backup restore flow /// Start database backup restore flow
/// ///
/// Put Immich into maintenance mode to restore a backup (Immich must not be configured) /// Put Immich into maintenance mode to restore a backup (Immich must not be configured)
/// ///
/// Note: This method returns the HTTP [Response]. /// Note: This method returns the HTTP [Response].
Future<Response> startRestoreFlowWithHttpInfo() async { Future<Response> startDatabaseRestoreFlowWithHttpInfo() async {
// ignore: prefer_const_declarations // ignore: prefer_const_declarations
final apiPath = r'/admin/database-backups/start-restore'; final apiPath = r'/admin/database-backups/start-restore';
@@ -200,11 +200,11 @@ class DatabaseBackupsAdminApi {
); );
} }
/// Start backup restore flow /// Start database backup restore flow
/// ///
/// Put Immich into maintenance mode to restore a backup (Immich must not be configured) /// Put Immich into maintenance mode to restore a backup (Immich must not be configured)
Future<void> startRestoreFlow() async { Future<void> startDatabaseRestoreFlow() async {
final response = await startRestoreFlowWithHttpInfo(); final response = await startDatabaseRestoreFlowWithHttpInfo();
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
} }
@@ -219,7 +219,7 @@ class DatabaseBackupsAdminApi {
/// Parameters: /// Parameters:
/// ///
/// * [MultipartFile] file: /// * [MultipartFile] file:
Future<Response> uploadBackupWithHttpInfo({ MultipartFile? file, }) async { Future<Response> uploadDatabaseBackupWithHttpInfo({ MultipartFile? file, }) async {
// ignore: prefer_const_declarations // ignore: prefer_const_declarations
final apiPath = r'/admin/database-backups/upload'; final apiPath = r'/admin/database-backups/upload';
@@ -261,8 +261,8 @@ class DatabaseBackupsAdminApi {
/// Parameters: /// Parameters:
/// ///
/// * [MultipartFile] file: /// * [MultipartFile] file:
Future<void> uploadBackup({ MultipartFile? file, }) async { Future<void> uploadDatabaseBackup({ MultipartFile? file, }) async {
final response = await uploadBackupWithHttpInfo( file: file, ); final response = await uploadDatabaseBackupWithHttpInfo( file: file, );
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
} }

View File

@@ -49,7 +49,7 @@ class MaintenanceAdminApi {
/// Detect existing install /// Detect existing install
/// ///
/// Collect integrity checks and other heuristics about local data. /// Collect integrity checks and other heuristics about local data.
Future<MaintenanceIntegrityResponseDto?> detectPriorInstall() async { Future<MaintenanceDetectInstallResponseDto?> detectPriorInstall() async {
final response = await detectPriorInstallWithHttpInfo(); final response = await detectPriorInstallWithHttpInfo();
if (response.statusCode >= HttpStatus.badRequest) { if (response.statusCode >= HttpStatus.badRequest) {
throw ApiException(response.statusCode, await _decodeBodyBytes(response)); throw ApiException(response.statusCode, await _decodeBodyBytes(response));
@@ -58,7 +58,7 @@ class MaintenanceAdminApi {
// At the time of writing this, `dart:convert` will throw an "Unexpected end of input" // At the time of writing this, `dart:convert` will throw an "Unexpected end of input"
// FormatException when trying to decode an empty string. // FormatException when trying to decode an empty string.
if (response.body.isNotEmpty && response.statusCode != HttpStatus.noContent) { if (response.body.isNotEmpty && response.statusCode != HttpStatus.noContent) {
return await apiClient.deserializeAsync(await _decodeBodyBytes(response), 'MaintenanceIntegrityResponseDto',) as MaintenanceIntegrityResponseDto; return await apiClient.deserializeAsync(await _decodeBodyBytes(response), 'MaintenanceDetectInstallResponseDto',) as MaintenanceDetectInstallResponseDto;
} }
return null; return null;

View File

@@ -384,16 +384,16 @@ class ApiClient {
return MaintenanceActionTypeTransformer().decode(value); return MaintenanceActionTypeTransformer().decode(value);
case 'MaintenanceAuthDto': case 'MaintenanceAuthDto':
return MaintenanceAuthDto.fromJson(value); return MaintenanceAuthDto.fromJson(value);
case 'MaintenanceIntegrityResponseDto': case 'MaintenanceDetectInstallResponseDto':
return MaintenanceIntegrityResponseDto.fromJson(value); return MaintenanceDetectInstallResponseDto.fromJson(value);
case 'MaintenanceDetectInstallStorageFolderDto':
return MaintenanceDetectInstallStorageFolderDto.fromJson(value);
case 'MaintenanceListBackupsResponseDto': case 'MaintenanceListBackupsResponseDto':
return MaintenanceListBackupsResponseDto.fromJson(value); return MaintenanceListBackupsResponseDto.fromJson(value);
case 'MaintenanceLoginDto': case 'MaintenanceLoginDto':
return MaintenanceLoginDto.fromJson(value); return MaintenanceLoginDto.fromJson(value);
case 'MaintenanceStatusResponseDto': case 'MaintenanceStatusResponseDto':
return MaintenanceStatusResponseDto.fromJson(value); return MaintenanceStatusResponseDto.fromJson(value);
case 'MaintenanceStorageFolderIntegrityDto':
return MaintenanceStorageFolderIntegrityDto.fromJson(value);
case 'ManualJobName': case 'ManualJobName':
return ManualJobNameTypeTransformer().decode(value); return ManualJobNameTypeTransformer().decode(value);
case 'MapMarkerResponseDto': case 'MapMarkerResponseDto':

View File

@@ -10,16 +10,16 @@
part of openapi.api; part of openapi.api;
class MaintenanceIntegrityResponseDto { class MaintenanceDetectInstallResponseDto {
/// Returns a new [MaintenanceIntegrityResponseDto] instance. /// Returns a new [MaintenanceDetectInstallResponseDto] instance.
MaintenanceIntegrityResponseDto({ MaintenanceDetectInstallResponseDto({
this.storage = const [], this.storage = const [],
}); });
List<MaintenanceStorageFolderIntegrityDto> storage; List<MaintenanceDetectInstallStorageFolderDto> storage;
@override @override
bool operator ==(Object other) => identical(this, other) || other is MaintenanceIntegrityResponseDto && bool operator ==(Object other) => identical(this, other) || other is MaintenanceDetectInstallResponseDto &&
_deepEquality.equals(other.storage, storage); _deepEquality.equals(other.storage, storage);
@override @override
@@ -28,7 +28,7 @@ class MaintenanceIntegrityResponseDto {
(storage.hashCode); (storage.hashCode);
@override @override
String toString() => 'MaintenanceIntegrityResponseDto[storage=$storage]'; String toString() => 'MaintenanceDetectInstallResponseDto[storage=$storage]';
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
final json = <String, dynamic>{}; final json = <String, dynamic>{};
@@ -36,26 +36,26 @@ class MaintenanceIntegrityResponseDto {
return json; return json;
} }
/// Returns a new [MaintenanceIntegrityResponseDto] instance and imports its values from /// Returns a new [MaintenanceDetectInstallResponseDto] instance and imports its values from
/// [value] if it's a [Map], null otherwise. /// [value] if it's a [Map], null otherwise.
// ignore: prefer_constructors_over_static_methods // ignore: prefer_constructors_over_static_methods
static MaintenanceIntegrityResponseDto? fromJson(dynamic value) { static MaintenanceDetectInstallResponseDto? fromJson(dynamic value) {
upgradeDto(value, "MaintenanceIntegrityResponseDto"); upgradeDto(value, "MaintenanceDetectInstallResponseDto");
if (value is Map) { if (value is Map) {
final json = value.cast<String, dynamic>(); final json = value.cast<String, dynamic>();
return MaintenanceIntegrityResponseDto( return MaintenanceDetectInstallResponseDto(
storage: MaintenanceStorageFolderIntegrityDto.listFromJson(json[r'storage']), storage: MaintenanceDetectInstallStorageFolderDto.listFromJson(json[r'storage']),
); );
} }
return null; return null;
} }
static List<MaintenanceIntegrityResponseDto> listFromJson(dynamic json, {bool growable = false,}) { static List<MaintenanceDetectInstallResponseDto> listFromJson(dynamic json, {bool growable = false,}) {
final result = <MaintenanceIntegrityResponseDto>[]; final result = <MaintenanceDetectInstallResponseDto>[];
if (json is List && json.isNotEmpty) { if (json is List && json.isNotEmpty) {
for (final row in json) { for (final row in json) {
final value = MaintenanceIntegrityResponseDto.fromJson(row); final value = MaintenanceDetectInstallResponseDto.fromJson(row);
if (value != null) { if (value != null) {
result.add(value); result.add(value);
} }
@@ -64,12 +64,12 @@ class MaintenanceIntegrityResponseDto {
return result.toList(growable: growable); return result.toList(growable: growable);
} }
static Map<String, MaintenanceIntegrityResponseDto> mapFromJson(dynamic json) { static Map<String, MaintenanceDetectInstallResponseDto> mapFromJson(dynamic json) {
final map = <String, MaintenanceIntegrityResponseDto>{}; final map = <String, MaintenanceDetectInstallResponseDto>{};
if (json is Map && json.isNotEmpty) { if (json is Map && json.isNotEmpty) {
json = json.cast<String, dynamic>(); // ignore: parameter_assignments json = json.cast<String, dynamic>(); // ignore: parameter_assignments
for (final entry in json.entries) { for (final entry in json.entries) {
final value = MaintenanceIntegrityResponseDto.fromJson(entry.value); final value = MaintenanceDetectInstallResponseDto.fromJson(entry.value);
if (value != null) { if (value != null) {
map[entry.key] = value; map[entry.key] = value;
} }
@@ -78,14 +78,14 @@ class MaintenanceIntegrityResponseDto {
return map; return map;
} }
// maps a json object with a list of MaintenanceIntegrityResponseDto-objects as value to a dart map // maps a json object with a list of MaintenanceDetectInstallResponseDto-objects as value to a dart map
static Map<String, List<MaintenanceIntegrityResponseDto>> mapListFromJson(dynamic json, {bool growable = false,}) { static Map<String, List<MaintenanceDetectInstallResponseDto>> mapListFromJson(dynamic json, {bool growable = false,}) {
final map = <String, List<MaintenanceIntegrityResponseDto>>{}; final map = <String, List<MaintenanceDetectInstallResponseDto>>{};
if (json is Map && json.isNotEmpty) { if (json is Map && json.isNotEmpty) {
// ignore: parameter_assignments // ignore: parameter_assignments
json = json.cast<String, dynamic>(); json = json.cast<String, dynamic>();
for (final entry in json.entries) { for (final entry in json.entries) {
map[entry.key] = MaintenanceIntegrityResponseDto.listFromJson(entry.value, growable: growable,); map[entry.key] = MaintenanceDetectInstallResponseDto.listFromJson(entry.value, growable: growable,);
} }
} }
return map; return map;

View File

@@ -10,9 +10,9 @@
part of openapi.api; part of openapi.api;
class MaintenanceStorageFolderIntegrityDto { class MaintenanceDetectInstallStorageFolderDto {
/// Returns a new [MaintenanceStorageFolderIntegrityDto] instance. /// Returns a new [MaintenanceDetectInstallStorageFolderDto] instance.
MaintenanceStorageFolderIntegrityDto({ MaintenanceDetectInstallStorageFolderDto({
required this.files, required this.files,
required this.folder, required this.folder,
required this.readable, required this.readable,
@@ -28,7 +28,7 @@ class MaintenanceStorageFolderIntegrityDto {
bool writable; bool writable;
@override @override
bool operator ==(Object other) => identical(this, other) || other is MaintenanceStorageFolderIntegrityDto && bool operator ==(Object other) => identical(this, other) || other is MaintenanceDetectInstallStorageFolderDto &&
other.files == files && other.files == files &&
other.folder == folder && other.folder == folder &&
other.readable == readable && other.readable == readable &&
@@ -43,7 +43,7 @@ class MaintenanceStorageFolderIntegrityDto {
(writable.hashCode); (writable.hashCode);
@override @override
String toString() => 'MaintenanceStorageFolderIntegrityDto[files=$files, folder=$folder, readable=$readable, writable=$writable]'; String toString() => 'MaintenanceDetectInstallStorageFolderDto[files=$files, folder=$folder, readable=$readable, writable=$writable]';
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
final json = <String, dynamic>{}; final json = <String, dynamic>{};
@@ -54,15 +54,15 @@ class MaintenanceStorageFolderIntegrityDto {
return json; return json;
} }
/// Returns a new [MaintenanceStorageFolderIntegrityDto] instance and imports its values from /// Returns a new [MaintenanceDetectInstallStorageFolderDto] instance and imports its values from
/// [value] if it's a [Map], null otherwise. /// [value] if it's a [Map], null otherwise.
// ignore: prefer_constructors_over_static_methods // ignore: prefer_constructors_over_static_methods
static MaintenanceStorageFolderIntegrityDto? fromJson(dynamic value) { static MaintenanceDetectInstallStorageFolderDto? fromJson(dynamic value) {
upgradeDto(value, "MaintenanceStorageFolderIntegrityDto"); upgradeDto(value, "MaintenanceDetectInstallStorageFolderDto");
if (value is Map) { if (value is Map) {
final json = value.cast<String, dynamic>(); final json = value.cast<String, dynamic>();
return MaintenanceStorageFolderIntegrityDto( return MaintenanceDetectInstallStorageFolderDto(
files: num.parse('${json[r'files']}'), files: num.parse('${json[r'files']}'),
folder: StorageFolder.fromJson(json[r'folder'])!, folder: StorageFolder.fromJson(json[r'folder'])!,
readable: mapValueOfType<bool>(json, r'readable')!, readable: mapValueOfType<bool>(json, r'readable')!,
@@ -72,11 +72,11 @@ class MaintenanceStorageFolderIntegrityDto {
return null; return null;
} }
static List<MaintenanceStorageFolderIntegrityDto> listFromJson(dynamic json, {bool growable = false,}) { static List<MaintenanceDetectInstallStorageFolderDto> listFromJson(dynamic json, {bool growable = false,}) {
final result = <MaintenanceStorageFolderIntegrityDto>[]; final result = <MaintenanceDetectInstallStorageFolderDto>[];
if (json is List && json.isNotEmpty) { if (json is List && json.isNotEmpty) {
for (final row in json) { for (final row in json) {
final value = MaintenanceStorageFolderIntegrityDto.fromJson(row); final value = MaintenanceDetectInstallStorageFolderDto.fromJson(row);
if (value != null) { if (value != null) {
result.add(value); result.add(value);
} }
@@ -85,12 +85,12 @@ class MaintenanceStorageFolderIntegrityDto {
return result.toList(growable: growable); return result.toList(growable: growable);
} }
static Map<String, MaintenanceStorageFolderIntegrityDto> mapFromJson(dynamic json) { static Map<String, MaintenanceDetectInstallStorageFolderDto> mapFromJson(dynamic json) {
final map = <String, MaintenanceStorageFolderIntegrityDto>{}; final map = <String, MaintenanceDetectInstallStorageFolderDto>{};
if (json is Map && json.isNotEmpty) { if (json is Map && json.isNotEmpty) {
json = json.cast<String, dynamic>(); // ignore: parameter_assignments json = json.cast<String, dynamic>(); // ignore: parameter_assignments
for (final entry in json.entries) { for (final entry in json.entries) {
final value = MaintenanceStorageFolderIntegrityDto.fromJson(entry.value); final value = MaintenanceDetectInstallStorageFolderDto.fromJson(entry.value);
if (value != null) { if (value != null) {
map[entry.key] = value; map[entry.key] = value;
} }
@@ -99,14 +99,14 @@ class MaintenanceStorageFolderIntegrityDto {
return map; return map;
} }
// maps a json object with a list of MaintenanceStorageFolderIntegrityDto-objects as value to a dart map // maps a json object with a list of MaintenanceDetectInstallStorageFolderDto-objects as value to a dart map
static Map<String, List<MaintenanceStorageFolderIntegrityDto>> mapListFromJson(dynamic json, {bool growable = false,}) { static Map<String, List<MaintenanceDetectInstallStorageFolderDto>> mapListFromJson(dynamic json, {bool growable = false,}) {
final map = <String, List<MaintenanceStorageFolderIntegrityDto>>{}; final map = <String, List<MaintenanceDetectInstallStorageFolderDto>>{};
if (json is Map && json.isNotEmpty) { if (json is Map && json.isNotEmpty) {
// ignore: parameter_assignments // ignore: parameter_assignments
json = json.cast<String, dynamic>(); json = json.cast<String, dynamic>();
for (final entry in json.entries) { for (final entry in json.entries) {
map[entry.key] = MaintenanceStorageFolderIntegrityDto.listFromJson(entry.value, growable: growable,); map[entry.key] = MaintenanceDetectInstallStorageFolderDto.listFromJson(entry.value, growable: growable,);
} }
} }
return map; return map;

View File

@@ -325,7 +325,7 @@
"/admin/database-backups": { "/admin/database-backups": {
"get": { "get": {
"description": "Get the list of the successful and failed backups", "description": "Get the list of the successful and failed backups",
"operationId": "listBackups", "operationId": "listDatabaseBackups",
"parameters": [], "parameters": [],
"responses": { "responses": {
"200": { "200": {
@@ -350,7 +350,7 @@
"api_key": [] "api_key": []
} }
], ],
"summary": "List backups", "summary": "List database backups",
"tags": [ "tags": [
"Database Backups (admin)" "Database Backups (admin)"
], ],
@@ -372,14 +372,14 @@
"/admin/database-backups/start-restore": { "/admin/database-backups/start-restore": {
"post": { "post": {
"description": "Put Immich into maintenance mode to restore a backup (Immich must not be configured)", "description": "Put Immich into maintenance mode to restore a backup (Immich must not be configured)",
"operationId": "startRestoreFlow", "operationId": "startDatabaseRestoreFlow",
"parameters": [], "parameters": [],
"responses": { "responses": {
"201": { "201": {
"description": "" "description": ""
} }
}, },
"summary": "Start backup restore flow", "summary": "Start database backup restore flow",
"tags": [ "tags": [
"Database Backups (admin)" "Database Backups (admin)"
], ],
@@ -399,7 +399,7 @@
"/admin/database-backups/upload": { "/admin/database-backups/upload": {
"post": { "post": {
"description": "Uploads .sql/.sql.gz file to restore backup from", "description": "Uploads .sql/.sql.gz file to restore backup from",
"operationId": "uploadBackup", "operationId": "uploadDatabaseBackup",
"parameters": [], "parameters": [],
"requestBody": { "requestBody": {
"content": { "content": {
@@ -450,7 +450,7 @@
"/admin/database-backups/{filename}": { "/admin/database-backups/{filename}": {
"delete": { "delete": {
"description": "Delete a backup by its filename", "description": "Delete a backup by its filename",
"operationId": "deleteBackup", "operationId": "deleteDatabaseBackup",
"parameters": [ "parameters": [
{ {
"name": "filename", "name": "filename",
@@ -478,7 +478,7 @@
"api_key": [] "api_key": []
} }
], ],
"summary": "Delete backup", "summary": "Delete database backup",
"tags": [ "tags": [
"Database Backups (admin)" "Database Backups (admin)"
], ],
@@ -498,7 +498,7 @@
}, },
"get": { "get": {
"description": "Downloads the database backup file", "description": "Downloads the database backup file",
"operationId": "downloadBackup", "operationId": "downloadDatabaseBackup",
"parameters": [ "parameters": [
{ {
"name": "filename", "name": "filename",
@@ -534,7 +534,7 @@
"api_key": [] "api_key": []
} }
], ],
"summary": "Download backup", "summary": "Download database backup",
"tags": [ "tags": [
"Database Backups (admin)" "Database Backups (admin)"
], ],

View File

@@ -50,14 +50,14 @@ export type SetMaintenanceModeDto = {
action: MaintenanceAction; action: MaintenanceAction;
restoreBackupFilename?: string; restoreBackupFilename?: string;
}; };
export type MaintenanceStorageFolderIntegrityDto = { export type MaintenanceDetectInstallStorageFolderDto = {
files: number; files: number;
folder: StorageFolder; folder: StorageFolder;
readable: boolean; readable: boolean;
writable: boolean; writable: boolean;
}; };
export type MaintenanceIntegrityResponseDto = { export type MaintenanceDetectInstallResponseDto = {
storage: MaintenanceStorageFolderIntegrityDto[]; storage: MaintenanceDetectInstallStorageFolderDto[];
}; };
export type MaintenanceLoginDto = { export type MaintenanceLoginDto = {
token?: string; token?: string;
@@ -1874,9 +1874,9 @@ export function unlinkAllOAuthAccountsAdmin(opts?: Oazapfts.RequestOpts) {
})); }));
} }
/** /**
* List backups * List database backups
*/ */
export function listBackups(opts?: Oazapfts.RequestOpts) { export function listDatabaseBackups(opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchJson<{ return oazapfts.ok(oazapfts.fetchJson<{
status: 200; status: 200;
data: MaintenanceListBackupsResponseDto; data: MaintenanceListBackupsResponseDto;
@@ -1885,9 +1885,9 @@ export function listBackups(opts?: Oazapfts.RequestOpts) {
})); }));
} }
/** /**
* Start backup restore flow * Start database backup restore flow
*/ */
export function startRestoreFlow(opts?: Oazapfts.RequestOpts) { export function startDatabaseRestoreFlow(opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchText("/admin/database-backups/start-restore", { return oazapfts.ok(oazapfts.fetchText("/admin/database-backups/start-restore", {
...opts, ...opts,
method: "POST" method: "POST"
@@ -1896,7 +1896,7 @@ export function startRestoreFlow(opts?: Oazapfts.RequestOpts) {
/** /**
* Upload database backup * Upload database backup
*/ */
export function uploadBackup({ maintenanceUploadBackupDto }: { export function uploadDatabaseBackup({ maintenanceUploadBackupDto }: {
maintenanceUploadBackupDto: MaintenanceUploadBackupDto; maintenanceUploadBackupDto: MaintenanceUploadBackupDto;
}, opts?: Oazapfts.RequestOpts) { }, opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchText("/admin/database-backups/upload", oazapfts.multipart({ return oazapfts.ok(oazapfts.fetchText("/admin/database-backups/upload", oazapfts.multipart({
@@ -1906,9 +1906,9 @@ export function uploadBackup({ maintenanceUploadBackupDto }: {
}))); })));
} }
/** /**
* Delete backup * Delete database backup
*/ */
export function deleteBackup({ filename }: { export function deleteDatabaseBackup({ filename }: {
filename: string; filename: string;
}, opts?: Oazapfts.RequestOpts) { }, opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchText(`/admin/database-backups/${encodeURIComponent(filename)}`, { return oazapfts.ok(oazapfts.fetchText(`/admin/database-backups/${encodeURIComponent(filename)}`, {
@@ -1917,9 +1917,9 @@ export function deleteBackup({ filename }: {
})); }));
} }
/** /**
* Download backup * Download database backup
*/ */
export function downloadBackup({ filename }: { export function downloadDatabaseBackup({ filename }: {
filename: string; filename: string;
}, opts?: Oazapfts.RequestOpts) { }, opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchBlob<{ return oazapfts.ok(oazapfts.fetchBlob<{
@@ -1947,7 +1947,7 @@ export function setMaintenanceMode({ setMaintenanceModeDto }: {
export function detectPriorInstall(opts?: Oazapfts.RequestOpts) { export function detectPriorInstall(opts?: Oazapfts.RequestOpts) {
return oazapfts.ok(oazapfts.fetchJson<{ return oazapfts.ok(oazapfts.fetchJson<{
status: 200; status: 200;
data: MaintenanceIntegrityResponseDto; data: MaintenanceDetectInstallResponseDto;
}>("/admin/maintenance/detect-install", { }>("/admin/maintenance/detect-install", {
...opts ...opts
})); }));

View File

@@ -25,24 +25,24 @@ export class DatabaseBackupController {
@Get() @Get()
@Endpoint({ @Endpoint({
summary: 'List backups', summary: 'List database backups',
description: 'Get the list of the successful and failed backups', description: 'Get the list of the successful and failed backups',
history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'), history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'),
}) })
@Authenticated({ permission: Permission.Maintenance, admin: true }) @Authenticated({ permission: Permission.Maintenance, admin: true })
listBackups(): Promise<MaintenanceListBackupsResponseDto> { listDatabaseBackups(): Promise<MaintenanceListBackupsResponseDto> {
return this.service.listBackups(); return this.service.listBackups();
} }
@Get(':filename') @Get(':filename')
@FileResponse() @FileResponse()
@Endpoint({ @Endpoint({
summary: 'Download backup', summary: 'Download database backup',
description: 'Downloads the database backup file', description: 'Downloads the database backup file',
history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'), history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'),
}) })
@Authenticated({ permission: Permission.BackupDownload, admin: true }) @Authenticated({ permission: Permission.BackupDownload, admin: true })
async downloadBackup( async downloadDatabaseBackup(
@Param() { filename }: FilenameParamDto, @Param() { filename }: FilenameParamDto,
@Res() res: Response, @Res() res: Response,
@Next() next: NextFunction, @Next() next: NextFunction,
@@ -52,22 +52,22 @@ export class DatabaseBackupController {
@Delete(':filename') @Delete(':filename')
@Endpoint({ @Endpoint({
summary: 'Delete backup', summary: 'Delete database backup',
description: 'Delete a backup by its filename', description: 'Delete a backup by its filename',
history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'), history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'),
}) })
@Authenticated({ permission: Permission.BackupDelete, admin: true }) @Authenticated({ permission: Permission.BackupDelete, admin: true })
async deleteBackup(@Param() { filename }: FilenameParamDto): Promise<void> { async deleteDatabaseBackup(@Param() { filename }: FilenameParamDto): Promise<void> {
return this.service.deleteBackup(filename); return this.service.deleteBackup(filename);
} }
@Post('start-restore') @Post('start-restore')
@Endpoint({ @Endpoint({
summary: 'Start backup restore flow', summary: 'Start database backup restore flow',
description: 'Put Immich into maintenance mode to restore a backup (Immich must not be configured)', description: 'Put Immich into maintenance mode to restore a backup (Immich must not be configured)',
history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'), history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'),
}) })
async startRestoreFlow( async startDatabaseRestoreFlow(
@GetLoginDetails() loginDetails: LoginDetails, @GetLoginDetails() loginDetails: LoginDetails,
@Res({ passthrough: true }) res: Response, @Res({ passthrough: true }) res: Response,
): Promise<void> { ): Promise<void> {
@@ -88,7 +88,7 @@ export class DatabaseBackupController {
history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'), history: new HistoryBuilder().added('v2.4.0').alpha('v2.4.0'),
}) })
@UseInterceptors(FileInterceptor('file')) @UseInterceptors(FileInterceptor('file'))
uploadBackup( uploadDatabaseBackup(
@UploadedFile() @UploadedFile()
file: Express.Multer.File, file: Express.Multer.File,
): Promise<void> { ): Promise<void> {

View File

@@ -32,6 +32,9 @@ import { sendFile } from 'src/utils/file';
import { respondWithCookie } from 'src/utils/response'; import { respondWithCookie } from 'src/utils/response';
import { FilenameParamDto } from 'src/validation'; import { FilenameParamDto } from 'src/validation';
import type { DatabaseBackupController as _DatabaseBackupController } from 'src/controllers/database-backup.controller';
import type { ServerController as _ServerController } from 'src/controllers/server.controller';
@Controller() @Controller()
export class MaintenanceWorkerController { export class MaintenanceWorkerController {
constructor( constructor(
@@ -39,11 +42,58 @@ export class MaintenanceWorkerController {
private service: MaintenanceWorkerService, private service: MaintenanceWorkerService,
) {} ) {}
/**
* {@link _ServerController.getServerConfig }
*/
@Get('server/config') @Get('server/config')
getServerConfig(): ServerConfigDto { getServerConfig(): ServerConfigDto {
return this.service.getSystemConfig(); return this.service.getSystemConfig();
} }
/**
* {@link _DatabaseBackupController.listDatabaseBackups}
*/
@Get('admin/database-backups')
@MaintenanceRoute()
listDatabaseBackups(): Promise<MaintenanceListBackupsResponseDto> {
return this.service.listBackups();
}
/**
* {@link _DatabaseBackupController.downloadDatabaseBackup}
*/
@Get('admin/database-backups/:filename')
@MaintenanceRoute()
async downloadDatabaseBackup(
@Param() { filename }: FilenameParamDto,
@Res() res: Response,
@Next() next: NextFunction,
) {
await sendFile(res, next, () => this.service.downloadBackup(filename), this.logger);
}
/**
* {@link _DatabaseBackupController.deleteDatabaseBackup}
*/
@Delete('admin/database-backups/:filename')
@MaintenanceRoute()
async deleteDatabaseBackup(@Param() { filename }: FilenameParamDto): Promise<void> {
return this.service.deleteBackup(filename);
}
/**
* {@link _DatabaseBackupController.uploadDatabaseBackup}
*/
@Post('admin/database-backups/upload')
@MaintenanceRoute()
@UseInterceptors(FileInterceptor('file'))
uploadDatabaseBackup(
@UploadedFile()
file: Express.Multer.File,
): Promise<void> {
return this.service.uploadBackup(file);
}
@Get('admin/maintenance/status') @Get('admin/maintenance/status')
maintenanceStatus(@Req() request: Request): Promise<MaintenanceStatusResponseDto> { maintenanceStatus(@Req() request: Request): Promise<MaintenanceStatusResponseDto> {
return this.service.status(request.cookies[ImmichCookie.MaintenanceToken]); return this.service.status(request.cookies[ImmichCookie.MaintenanceToken]);
@@ -74,32 +124,4 @@ export class MaintenanceWorkerController {
setMaintenanceMode(@Body() dto: SetMaintenanceModeDto): void { setMaintenanceMode(@Body() dto: SetMaintenanceModeDto): void {
void this.service.setAction(dto); void this.service.setAction(dto);
} }
@Get('admin/database-backups')
@MaintenanceRoute()
listBackups(): Promise<MaintenanceListBackupsResponseDto> {
return this.service.listBackups();
}
@Get('admin/database-backups/:filename')
@MaintenanceRoute()
async downloadBackup(@Param() { filename }: FilenameParamDto, @Res() res: Response, @Next() next: NextFunction) {
await sendFile(res, next, () => this.service.downloadBackup(filename), this.logger);
}
@Delete('admin/database-backups/:filename')
@MaintenanceRoute()
async deleteBackup(@Param() { filename }: FilenameParamDto): Promise<void> {
return this.service.deleteBackup(filename);
}
@Post('admin/database-backups/upload')
@MaintenanceRoute()
@UseInterceptors(FileInterceptor('file'))
uploadBackup(
@UploadedFile()
file: Express.Multer.File,
): Promise<void> {
return this.service.uploadBackup(file);
}
} }

View File

@@ -3,9 +3,9 @@
import { openFilePicker } from '$lib/utils/file-uploader'; import { openFilePicker } from '$lib/utils/file-uploader';
import { handleError } from '$lib/utils/handle-error'; import { handleError } from '$lib/utils/handle-error';
import { import {
deleteBackup, deleteDatabaseBackup,
getBaseUrl, getBaseUrl,
listBackups, listDatabaseBackups,
MaintenanceAction, MaintenanceAction,
setMaintenanceMode, setMaintenanceMode,
type MaintenanceUploadBackupDto, type MaintenanceUploadBackupDto,
@@ -55,7 +55,7 @@
onMount(async () => { onMount(async () => {
if (!props.backups) { if (!props.backups) {
const result = await listBackups(); const result = await listDatabaseBackups();
backups = mapBackups(result.backups); backups = mapBackups(result.backups);
} }
}); });
@@ -92,7 +92,7 @@
try { try {
deleting.add(filename); deleting.add(filename);
await deleteBackup({ await deleteDatabaseBackup({
filename, filename,
}); });
@@ -151,7 +151,7 @@
uploadProgress = 1; uploadProgress = 1;
const { backups: newList } = await listBackups(); const { backups: newList } = await listDatabaseBackups();
backups = mapBackups(newList); backups = mapBackups(newList);
} catch (error) { } catch (error) {
handleError(error, $t('admin.maintenance_upload_backup_error')); handleError(error, $t('admin.maintenance_upload_backup_error'));

View File

@@ -3,7 +3,7 @@
import { AppRoute } from '$lib/constants'; import { AppRoute } from '$lib/constants';
import { websocketStore } from '$lib/stores/websocket'; import { websocketStore } from '$lib/stores/websocket';
import { handleError } from '$lib/utils/handle-error'; import { handleError } from '$lib/utils/handle-error';
import { startRestoreFlow } from '@immich/sdk'; import { startDatabaseRestoreFlow } from '@immich/sdk';
import { Button, Heading, Stack } from '@immich/ui'; import { Button, Heading, Stack } from '@immich/ui';
import { t } from 'svelte-i18n'; import { t } from 'svelte-i18n';
@@ -13,7 +13,7 @@
isMaintenanceMode: true, isMaintenanceMode: true,
}); });
await startRestoreFlow(); await startDatabaseRestoreFlow();
} catch (error) { } catch (error) {
handleError(error, $t('admin.maintenance_start_error')); handleError(error, $t('admin.maintenance_start_error'));
} }

View File

@@ -1,11 +1,11 @@
import { authenticate } from '$lib/utils/auth'; import { authenticate } from '$lib/utils/auth';
import { getFormatter } from '$lib/utils/i18n'; import { getFormatter } from '$lib/utils/i18n';
import { listBackups } from '@immich/sdk'; import { listDatabaseBackups } from '@immich/sdk';
import type { PageLoad } from './$types'; import type { PageLoad } from './$types';
export const load = (async ({ url }) => { export const load = (async ({ url }) => {
await authenticate(url, { admin: true }); await authenticate(url, { admin: true });
const { backups } = await listBackups(); const { backups } = await listDatabaseBackups();
const $t = await getFormatter(); const $t = await getFormatter();
return { return {