mirror of
https://github.com/twonlyapp/twonly-app.git
synced 2026-01-15 11:18:41 +00:00
upload non finished uploads after restart
This commit is contained in:
parent
cb1ad9bdc7
commit
404aee1e18
6 changed files with 54 additions and 5 deletions
|
|
@ -17,6 +17,7 @@ import 'package:twonly/src/providers/image_editor.provider.dart';
|
||||||
import 'package:twonly/src/providers/settings.provider.dart';
|
import 'package:twonly/src/providers/settings.provider.dart';
|
||||||
import 'package:twonly/src/services/api.service.dart';
|
import 'package:twonly/src/services/api.service.dart';
|
||||||
import 'package:twonly/src/services/api/mediafiles/media_background.service.dart';
|
import 'package:twonly/src/services/api/mediafiles/media_background.service.dart';
|
||||||
|
import 'package:twonly/src/services/api/mediafiles/upload.service.dart';
|
||||||
import 'package:twonly/src/services/fcm.service.dart';
|
import 'package:twonly/src/services/fcm.service.dart';
|
||||||
import 'package:twonly/src/services/mediafiles/mediafile.service.dart';
|
import 'package:twonly/src/services/mediafiles/mediafile.service.dart';
|
||||||
import 'package:twonly/src/utils/log.dart';
|
import 'package:twonly/src/utils/log.dart';
|
||||||
|
|
@ -55,6 +56,7 @@ void main() async {
|
||||||
twonlyDB = TwonlyDB();
|
twonlyDB = TwonlyDB();
|
||||||
|
|
||||||
await initFileDownloader();
|
await initFileDownloader();
|
||||||
|
unawaited(finishStartedPreprocessing());
|
||||||
|
|
||||||
unawaited(MediaFileService.purgeTempFolder());
|
unawaited(MediaFileService.purgeTempFolder());
|
||||||
await twonlyDB.messagesDao.purgeMessageTable();
|
await twonlyDB.messagesDao.purgeMessageTable();
|
||||||
|
|
|
||||||
|
|
@ -84,6 +84,16 @@ class MediaFilesDao extends DatabaseAccessor<TwonlyDB>
|
||||||
.get();
|
.get();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<List<MediaFile>> getAllMediaFilesPendingUpload() async {
|
||||||
|
return (select(mediaFiles)
|
||||||
|
..where(
|
||||||
|
(t) =>
|
||||||
|
t.uploadState.equals(UploadState.initialized.name) |
|
||||||
|
t.uploadState.equals(UploadState.preprocessing.name),
|
||||||
|
))
|
||||||
|
.get();
|
||||||
|
}
|
||||||
|
|
||||||
Stream<List<MediaFile>> watchAllStoredMediaFiles() {
|
Stream<List<MediaFile>> watchAllStoredMediaFiles() {
|
||||||
return (select(mediaFiles)..where((t) => t.stored.equals(true))).watch();
|
return (select(mediaFiles)..where((t) => t.stored.equals(true))).watch();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -19,6 +19,20 @@ import 'package:twonly/src/services/mediafiles/mediafile.service.dart';
|
||||||
import 'package:twonly/src/utils/log.dart';
|
import 'package:twonly/src/utils/log.dart';
|
||||||
import 'package:twonly/src/utils/misc.dart';
|
import 'package:twonly/src/utils/misc.dart';
|
||||||
|
|
||||||
|
Future<void> finishStartedPreprocessing() async {
|
||||||
|
final mediaFiles =
|
||||||
|
await twonlyDB.mediaFilesDao.getAllMediaFilesPendingUpload();
|
||||||
|
|
||||||
|
for (final mediaFile in mediaFiles) {
|
||||||
|
try {
|
||||||
|
final service = await MediaFileService.fromMedia(mediaFile);
|
||||||
|
await startBackgroundMediaUpload(service);
|
||||||
|
} catch (e) {
|
||||||
|
Log.error(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Future<MediaFileService?> initializeMediaUpload(
|
Future<MediaFileService?> initializeMediaUpload(
|
||||||
MediaType type,
|
MediaType type,
|
||||||
int? displayLimitInMilliseconds,
|
int? displayLimitInMilliseconds,
|
||||||
|
|
@ -77,15 +91,22 @@ Future<void> startBackgroundMediaUpload(MediaFileService mediaService) async {
|
||||||
|
|
||||||
if (!mediaService.tempPath.existsSync()) {
|
if (!mediaService.tempPath.existsSync()) {
|
||||||
await mediaService.compressMedia();
|
await mediaService.compressMedia();
|
||||||
|
if (!mediaService.tempPath.existsSync()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mediaService.encryptedPath.existsSync()) {
|
if (!mediaService.encryptedPath.existsSync()) {
|
||||||
await _encryptMediaFiles(mediaService);
|
await _encryptMediaFiles(mediaService);
|
||||||
|
if (!mediaService.encryptedPath.existsSync()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!mediaService.uploadRequestPath.existsSync()) {
|
if (!mediaService.uploadRequestPath.existsSync()) {
|
||||||
await _createUploadRequest(mediaService);
|
await _createUploadRequest(mediaService);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mediaService.uploadRequestPath.existsSync()) {
|
if (mediaService.uploadRequestPath.existsSync()) {
|
||||||
await mediaService.setUploadState(UploadState.uploading);
|
await mediaService.setUploadState(UploadState.uploading);
|
||||||
// at this point the original file is not used any more, so it can be deleted
|
// at this point the original file is not used any more, so it can be deleted
|
||||||
|
|
@ -101,6 +122,11 @@ Future<void> startBackgroundMediaUpload(MediaFileService mediaService) async {
|
||||||
Future<void> _encryptMediaFiles(MediaFileService mediaService) async {
|
Future<void> _encryptMediaFiles(MediaFileService mediaService) async {
|
||||||
/// if there is a video wait until it is finished with compression
|
/// if there is a video wait until it is finished with compression
|
||||||
|
|
||||||
|
if (!mediaService.tempPath.existsSync()) {
|
||||||
|
Log.error('Could not encrypted image as it does not exists');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
final dataToEncrypt = await mediaService.tempPath.readAsBytes();
|
final dataToEncrypt = await mediaService.tempPath.readAsBytes();
|
||||||
|
|
||||||
final chacha20 = FlutterChacha20.poly1305Aead();
|
final chacha20 = FlutterChacha20.poly1305Aead();
|
||||||
|
|
|
||||||
|
|
@ -10,7 +10,7 @@ Future<void> createThumbnailsForVideo(
|
||||||
final stopwatch = Stopwatch()..start();
|
final stopwatch = Stopwatch()..start();
|
||||||
|
|
||||||
final command =
|
final command =
|
||||||
'-i ${sourceFile.path} -ss 00:00:00 -vframes 1 -vf "scale=iw:ih:flags=lanczos" -c:v libwebp -q:v 100 -compression_level 6 ${destinationFile.path}';
|
'-i "${sourceFile.path}" -ss 00:00:00 -vframes 1 -vf "scale=iw:ih:flags=lanczos" -c:v libwebp -q:v 100 -compression_level 6 "${destinationFile.path}"';
|
||||||
|
|
||||||
final session = await FFmpegKit.execute(command);
|
final session = await FFmpegKit.execute(command);
|
||||||
final returnCode = await session.getReturnCode();
|
final returnCode = await session.getReturnCode();
|
||||||
|
|
@ -22,8 +22,9 @@ Future<void> createThumbnailsForVideo(
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
Log.info(command);
|
Log.info(command);
|
||||||
Log.error('Compression failed for the video with exit code $returnCode.');
|
Log.error(
|
||||||
|
'Thumbnail creation failed for the video with exit code $returnCode.',
|
||||||
|
);
|
||||||
Log.error(await session.getAllLogsAsString());
|
Log.error(await session.getAllLogsAsString());
|
||||||
// Report this error to the user?
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -108,7 +108,6 @@ class ChatTextEntry extends StatelessWidget {
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
// if (displayTime)
|
|
||||||
Text(
|
Text(
|
||||||
friendlyTime(
|
friendlyTime(
|
||||||
context,
|
context,
|
||||||
|
|
|
||||||
|
|
@ -20,9 +20,19 @@ class MemoriesItemThumbnail extends StatefulWidget {
|
||||||
class _MemoriesItemThumbnailState extends State<MemoriesItemThumbnail> {
|
class _MemoriesItemThumbnailState extends State<MemoriesItemThumbnail> {
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
|
initAsync();
|
||||||
super.initState();
|
super.initState();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<void> initAsync() async {
|
||||||
|
if (!widget.galleryItem.mediaService.thumbnailPath.existsSync()) {
|
||||||
|
if (widget.galleryItem.mediaService.storedPath.existsSync()) {
|
||||||
|
await widget.galleryItem.mediaService.createThumbnail();
|
||||||
|
if (mounted) setState(() {});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
super.dispose();
|
super.dispose();
|
||||||
|
|
@ -46,7 +56,8 @@ class _MemoriesItemThumbnailState extends State<MemoriesItemThumbnail> {
|
||||||
children: [
|
children: [
|
||||||
if (media.thumbnailPath.existsSync())
|
if (media.thumbnailPath.existsSync())
|
||||||
Image.file(media.thumbnailPath)
|
Image.file(media.thumbnailPath)
|
||||||
else if (media.storedPath.existsSync())
|
else if (media.storedPath.existsSync() &&
|
||||||
|
media.mediaFile.type == MediaType.image)
|
||||||
Image.file(media.storedPath)
|
Image.file(media.storedPath)
|
||||||
else
|
else
|
||||||
const Text('Media file removed.'),
|
const Text('Media file removed.'),
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue