mirror of
https://github.com/immich-app/immich
synced 2025-11-14 17:36:12 +00:00
revert redundant changes
This commit is contained in:
parent
113470c87a
commit
9964ad50c2
4 changed files with 46 additions and 86 deletions
|
|
@ -24,7 +24,6 @@ import java.security.MessageDigest
|
||||||
import java.io.FileInputStream
|
import java.io.FileInputStream
|
||||||
import kotlinx.coroutines.*
|
import kotlinx.coroutines.*
|
||||||
import androidx.core.net.toUri
|
import androidx.core.net.toUri
|
||||||
import java.io.InputStream
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Android plugin for Dart `BackgroundService` and file trash operations
|
* Android plugin for Dart `BackgroundService` and file trash operations
|
||||||
|
|
@ -156,11 +155,10 @@ class BackgroundServicePlugin : FlutterPlugin, MethodChannel.MethodCallHandler,
|
||||||
"restoreFromTrash" -> {
|
"restoreFromTrash" -> {
|
||||||
val fileName = call.argument<String>("fileName")
|
val fileName = call.argument<String>("fileName")
|
||||||
val type = call.argument<Int>("type")
|
val type = call.argument<Int>("type")
|
||||||
val checksum = call.argument<String>("checksum")
|
|
||||||
val mediaId = call.argument<String>("mediaId")
|
val mediaId = call.argument<String>("mediaId")
|
||||||
if (fileName != null && type != null && checksum != null) {
|
if (fileName != null && type != null) {
|
||||||
if ((Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) && hasManageMediaPermission()) {
|
if ((Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) && hasManageMediaPermission()) {
|
||||||
restoreFromTrash(fileName, type, checksum, result)
|
restoreFromTrash(fileName, type, result)
|
||||||
} else {
|
} else {
|
||||||
result.error("PERMISSION_DENIED", "Media permission required", null)
|
result.error("PERMISSION_DENIED", "Media permission required", null)
|
||||||
}
|
}
|
||||||
|
|
@ -222,14 +220,14 @@ class BackgroundServicePlugin : FlutterPlugin, MethodChannel.MethodCallHandler,
|
||||||
}
|
}
|
||||||
|
|
||||||
@RequiresApi(Build.VERSION_CODES.R)
|
@RequiresApi(Build.VERSION_CODES.R)
|
||||||
private fun restoreFromTrash(name: String, type: Int, checksum: String, result: Result) {
|
private fun restoreFromTrash(name: String, type: Int, result: Result) {
|
||||||
val uri = getTrashedFileUri(name, type, checksum)
|
val uri = getTrashedFileUri(name, type)
|
||||||
if (uri == null) {
|
if (uri == null) {
|
||||||
Log.e(TAG, "TrashError, Asset Uri cannot be found obtained")
|
Log.e("TrashError", "Asset Uri cannot be found obtained")
|
||||||
result.error("TrashError", "Asset Uri cannot be found obtained", null)
|
result.error("TrashError", "Asset Uri cannot be found obtained", null)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
Log.i(TAG, "trying to restore from trash FILE_URI - $uri")
|
Log.e("FILE_URI", uri.toString())
|
||||||
uri.let { toggleTrash(listOf(it), false, result) }
|
uri.let { toggleTrash(listOf(it), false, result) }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -265,6 +263,7 @@ class BackgroundServicePlugin : FlutterPlugin, MethodChannel.MethodCallHandler,
|
||||||
result.error("TrashError", "Activity or ContentResolver not available", null)
|
result.error("TrashError", "Activity or ContentResolver not available", null)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
val pendingIntent = MediaStore.createTrashRequest(contentResolver, contentUris, isTrashed)
|
val pendingIntent = MediaStore.createTrashRequest(contentResolver, contentUris, isTrashed)
|
||||||
pendingResult = result // Store for onActivityResult
|
pendingResult = result // Store for onActivityResult
|
||||||
|
|
@ -274,62 +273,39 @@ class BackgroundServicePlugin : FlutterPlugin, MethodChannel.MethodCallHandler,
|
||||||
null, 0, 0, 0
|
null, 0, 0, 0
|
||||||
)
|
)
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
Log.e(TAG, "TrashError, Error creating or starting trash request", e)
|
Log.e("TrashError", "Error creating or starting trash request", e)
|
||||||
result.error("TrashError", "Error creating or starting trash request", null)
|
result.error("TrashError", "Error creating or starting trash request", null)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@RequiresApi(Build.VERSION_CODES.R)
|
@RequiresApi(Build.VERSION_CODES.R)
|
||||||
private fun getTrashedFileUri(fileName: String, type: Int, checksum: String): Uri? {
|
private fun getTrashedFileUri(fileName: String, type: Int): Uri? {
|
||||||
val contentResolver = context?.contentResolver ?: return null
|
val contentResolver = context?.contentResolver ?: return null
|
||||||
val queryUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL)
|
val queryUri = MediaStore.Files.getContentUri(MediaStore.VOLUME_EXTERNAL)
|
||||||
val projection = arrayOf(
|
val projection = arrayOf(MediaStore.Files.FileColumns._ID)
|
||||||
MediaStore.Files.FileColumns._ID,
|
|
||||||
MediaStore.Files.FileColumns.DISPLAY_NAME
|
|
||||||
)
|
|
||||||
|
|
||||||
val dotIndex = fileName.lastIndexOf('.')
|
|
||||||
val baseName = if (dotIndex != -1) fileName.substring(0, dotIndex) else fileName
|
|
||||||
val extension = if (dotIndex != -1) fileName.substring(dotIndex) else ""
|
|
||||||
val nameLike = "%${baseName}%${extension}"
|
|
||||||
|
|
||||||
val queryArgs = Bundle().apply {
|
val queryArgs = Bundle().apply {
|
||||||
putString(ContentResolver.QUERY_ARG_SQL_SELECTION, "${MediaStore.Files.FileColumns.DISPLAY_NAME} LIKE ?")
|
putString(
|
||||||
putStringArray(ContentResolver.QUERY_ARG_SQL_SELECTION_ARGS, arrayOf(nameLike))
|
ContentResolver.QUERY_ARG_SQL_SELECTION,
|
||||||
|
"${MediaStore.Files.FileColumns.DISPLAY_NAME} = ?"
|
||||||
|
)
|
||||||
|
putStringArray(ContentResolver.QUERY_ARG_SQL_SELECTION_ARGS, arrayOf(fileName))
|
||||||
putInt(MediaStore.QUERY_ARG_MATCH_TRASHED, MediaStore.MATCH_ONLY)
|
putInt(MediaStore.QUERY_ARG_MATCH_TRASHED, MediaStore.MATCH_ONLY)
|
||||||
}
|
}
|
||||||
|
|
||||||
val expectedBytes = try {
|
|
||||||
android.util.Base64.decode(checksum, android.util.Base64.DEFAULT)
|
|
||||||
} catch (e: Exception) {
|
|
||||||
Log.e(TAG, "getTrashedFileUri, invalid Base64 checksum: $checksum, Exception: $e")
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
|
|
||||||
contentResolver.query(queryUri, projection, queryArgs, null)?.use { cursor ->
|
contentResolver.query(queryUri, projection, queryArgs, null)?.use { cursor ->
|
||||||
val idxId = cursor.getColumnIndexOrThrow(MediaStore.Files.FileColumns._ID)
|
if (cursor.moveToFirst()) {
|
||||||
val idxName = cursor.getColumnIndexOrThrow(MediaStore.Files.FileColumns.DISPLAY_NAME)
|
val id = cursor.getLong(cursor.getColumnIndexOrThrow(MediaStore.Files.FileColumns._ID))
|
||||||
|
// same order as AssetType from dart
|
||||||
while (cursor.moveToNext()) {
|
val contentUri = when (type) {
|
||||||
val id = cursor.getLong(idxId)
|
1 -> MediaStore.Images.Media.EXTERNAL_CONTENT_URI
|
||||||
val dn = cursor.getString(idxName)
|
2 -> MediaStore.Video.Media.EXTERNAL_CONTENT_URI
|
||||||
|
3 -> MediaStore.Audio.Media.EXTERNAL_CONTENT_URI
|
||||||
val candidateUri = ContentUris.withAppendedId(queryUri, id)
|
else -> queryUri
|
||||||
|
}
|
||||||
val sha1Bytes = try {
|
|
||||||
contentResolver.openInputStream(candidateUri)?.use { ins -> sha1OfStream(ins) }
|
|
||||||
} catch (e: Exception) {
|
|
||||||
Log.e(TAG, "getTrashedFileUri, hash failed for $dn: ${e.message}")
|
|
||||||
null
|
|
||||||
} ?: continue
|
|
||||||
|
|
||||||
if (sha1Bytes.contentEquals(expectedBytes)) {
|
|
||||||
val contentUri = contentUriForType(type)
|
|
||||||
return ContentUris.withAppendedId(contentUri, id)
|
return ContentUris.withAppendedId(contentUri, id)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
Log.w(TAG, "getTrashedFileUri, not found by checksum, nameLike=$nameLike, checksum: $checksum")
|
|
||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -396,18 +372,6 @@ class BackgroundServicePlugin : FlutterPlugin, MethodChannel.MethodCallHandler,
|
||||||
toggleTrash(uris, false, result)
|
toggleTrash(uris, false, result)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun sha1OfStream(ins: InputStream): ByteArray {
|
|
||||||
val buf = ByteArray(BUFFER_SIZE)
|
|
||||||
val md = MessageDigest.getInstance("SHA-1")
|
|
||||||
var len: Int
|
|
||||||
while (true) {
|
|
||||||
len = ins.read(buf)
|
|
||||||
if (len <= 0) break
|
|
||||||
md.update(buf, 0, len)
|
|
||||||
}
|
|
||||||
return md.digest()
|
|
||||||
}
|
|
||||||
|
|
||||||
@RequiresApi(Build.VERSION_CODES.Q)
|
@RequiresApi(Build.VERSION_CODES.Q)
|
||||||
private fun contentUriForType(type: Int): Uri =
|
private fun contentUriForType(type: Int): Uri =
|
||||||
when (type) {
|
when (type) {
|
||||||
|
|
|
||||||
|
|
@ -14,8 +14,8 @@ class LocalFilesManagerRepository {
|
||||||
return await _service.moveToTrash(mediaUrls);
|
return await _service.moveToTrash(mediaUrls);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> restoreFromTrash(String fileName, int type, String checksum) async {
|
Future<bool> restoreFromTrash(String fileName, int type) async {
|
||||||
return await _service.restoreFromTrash(fileName, type, checksum);
|
return await _service.restoreFromTrash(fileName, type);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> restoreFromTrashById(String mediaId, int type) async {
|
Future<bool> restoreFromTrashById(String mediaId, int type) async {
|
||||||
|
|
|
||||||
|
|
@ -18,13 +18,9 @@ class LocalFilesManagerService {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> restoreFromTrash(String fileName, int type, String checksum) async {
|
Future<bool> restoreFromTrash(String fileName, int type) async {
|
||||||
try {
|
try {
|
||||||
return await _channel.invokeMethod('restoreFromTrash', {
|
return await _channel.invokeMethod('restoreFromTrash', {'fileName': fileName, 'type': type});
|
||||||
'fileName': fileName,
|
|
||||||
'type': type,
|
|
||||||
'checksum': checksum,
|
|
||||||
});
|
|
||||||
} catch (e, s) {
|
} catch (e, s) {
|
||||||
_logger.warning('Error restore file from trash', e, s);
|
_logger.warning('Error restore file from trash', e, s);
|
||||||
return false;
|
return false;
|
||||||
|
|
|
||||||
|
|
@ -691,7 +691,7 @@ class SyncService {
|
||||||
}
|
}
|
||||||
trashMediaUrls.add(mediaUrl);
|
trashMediaUrls.add(mediaUrl);
|
||||||
} else {
|
} else {
|
||||||
await _localFilesManager.restoreFromTrash(asset.fileName, asset.type.index, asset.checksum);
|
await _localFilesManager.restoreFromTrash(asset.fileName, asset.type.index);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue