import pica data

This commit is contained in:
2024-12-01 18:06:19 +08:00
committed by nyne
parent 305ef9263d
commit a711335012
3 changed files with 173 additions and 57 deletions

View File

@@ -110,16 +110,23 @@ class _AppSettingsState extends State<AppSettings> {
title: "Import App Data".tl, title: "Import App Data".tl,
callback: () async { callback: () async {
var controller = showLoadingDialog(context); var controller = showLoadingDialog(context);
var file = await selectFile(ext: ['venera']); var file = await selectFile(ext: ['venera', 'picadata']);
if (file != null) { if (file != null) {
var cacheFile = File(FilePath.join(App.cachePath, "temp.venera")); var cacheFile = File(FilePath.join(App.cachePath, "import_data_temp"));
await file.saveTo(cacheFile.path); await file.saveTo(cacheFile.path);
try { try {
if(file.name.endsWith('picadata')) {
await importPicaData(cacheFile);
} else {
await importAppData(cacheFile); await importAppData(cacheFile);
}
} catch (e, s) { } catch (e, s) {
Log.error("Import data", e.toString(), s); Log.error("Import data", e.toString(), s);
context.showMessage(message: "Failed to import data".tl); context.showMessage(message: "Failed to import data".tl);
} }
finally {
cacheFile.deleteIgnoreError();
}
} }
controller.close(); controller.close();
}, },

View File

@@ -1,11 +1,14 @@
import 'dart:convert'; import 'dart:convert';
import 'dart:isolate'; import 'dart:isolate';
import 'package:sqlite3/sqlite3.dart';
import 'package:venera/foundation/app.dart'; import 'package:venera/foundation/app.dart';
import 'package:venera/foundation/appdata.dart'; import 'package:venera/foundation/appdata.dart';
import 'package:venera/foundation/comic_source/comic_source.dart'; import 'package:venera/foundation/comic_source/comic_source.dart';
import 'package:venera/foundation/comic_type.dart';
import 'package:venera/foundation/favorites.dart'; import 'package:venera/foundation/favorites.dart';
import 'package:venera/foundation/history.dart'; import 'package:venera/foundation/history.dart';
import 'package:venera/foundation/log.dart';
import 'package:venera/network/cookie_jar.dart'; import 'package:venera/network/cookie_jar.dart';
import 'package:zip_flutter/zip_flutter.dart'; import 'package:zip_flutter/zip_flutter.dart';
@@ -43,6 +46,11 @@ Future<File> exportAppData() async {
Future<void> importAppData(File file, [bool checkVersion = false]) async { Future<void> importAppData(File file, [bool checkVersion = false]) async {
var cacheDirPath = FilePath.join(App.cachePath, 'temp_data'); var cacheDirPath = FilePath.join(App.cachePath, 'temp_data');
var cacheDir = Directory(cacheDirPath); var cacheDir = Directory(cacheDirPath);
if (cacheDir.existsSync()) {
cacheDir.deleteSync(recursive: true);
}
cacheDir.createSync();
try {
await Isolate.run(() { await Isolate.run(() {
ZipFile.openAndExtract(file.path, cacheDirPath); ZipFile.openAndExtract(file.path, cacheDirPath);
}); });
@@ -65,7 +73,8 @@ Future<void> importAppData(File file, [bool checkVersion = false]) async {
} }
if (await localFavoriteFile.exists()) { if (await localFavoriteFile.exists()) {
LocalFavoritesManager().close(); LocalFavoritesManager().close();
File(FilePath.join(App.dataPath, "local_favorite.db")).deleteIfExistsSync(); File(FilePath.join(App.dataPath, "local_favorite.db"))
.deleteIfExistsSync();
localFavoriteFile localFavoriteFile
.renameSync(FilePath.join(App.dataPath, "local_favorite.db")); .renameSync(FilePath.join(App.dataPath, "local_favorite.db"));
LocalFavoritesManager().init(); LocalFavoritesManager().init();
@@ -93,11 +102,109 @@ Future<void> importAppData(File file, [bool checkVersion = false]) async {
if (Directory(comicSourceDir).existsSync()) { if (Directory(comicSourceDir).existsSync()) {
for (var file in Directory(comicSourceDir).listSync()) { for (var file in Directory(comicSourceDir).listSync()) {
if (file is File) { if (file is File) {
var targetFile = FilePath.join(App.dataPath, "comic_source", file.name); var targetFile =
FilePath.join(App.dataPath, "comic_source", file.name);
File(targetFile).deleteIfExistsSync(); File(targetFile).deleteIfExistsSync();
await file.copy(targetFile); await file.copy(targetFile);
} }
} }
await ComicSource.reload(); await ComicSource.reload();
} }
} finally {
cacheDir.deleteIgnoreError(recursive: true);
}
}
Future<void> importPicaData(File file) async {
var cacheDirPath = FilePath.join(App.cachePath, 'temp_data');
var cacheDir = Directory(cacheDirPath);
if (cacheDir.existsSync()) {
cacheDir.deleteSync(recursive: true);
}
cacheDir.createSync();
try {
await Isolate.run(() {
ZipFile.openAndExtract(file.path, cacheDirPath);
});
var localFavoriteFile = cacheDir.joinFile("local_favorite.db");
if (localFavoriteFile.existsSync()) {
var db = sqlite3.open(localFavoriteFile.path);
try {
var folderNames = db
.select("SELECT name FROM sqlite_master WHERE type='table';")
.map((e) => e["name"] as String)
.toList();
folderNames.removeWhere((e) => e == "folder_order" || e == "folder_sync");
for (var folderName in folderNames) {
if (!LocalFavoritesManager().existsFolder(folderName)) {
LocalFavoritesManager().createFolder(folderName);
}
for (var comic in db.select("SELECT * FROM \"$folderName\";")) {
LocalFavoritesManager().addComic(
folderName,
FavoriteItem(
id: comic['target'],
name: comic['name'],
coverPath: comic['cover_path'],
author: comic['author'],
type: ComicType(switch(comic['type']) {
0 => 'picacg'.hashCode,
1 => 'ehentai'.hashCode,
2 => 'jm'.hashCode,
3 => 'hitomi'.hashCode,
4 => 'wnacg'.hashCode,
6 => 'nhentai'.hashCode,
_ => comic['type']
}),
tags: comic['tags'].split(','),
),
);
}
}
}
catch(e) {
Log.error("Import Data", "Failed to import local favorite: $e");
}
finally {
db.dispose();
}
}
var historyFile = cacheDir.joinFile("history.db");
if (historyFile.existsSync()) {
var db = sqlite3.open(historyFile.path);
try {
for (var comic in db.select("SELECT * FROM history;")) {
HistoryManager().addHistory(
History.fromMap({
"type": switch(comic['type']) {
0 => 'picacg'.hashCode,
1 => 'ehentai'.hashCode,
2 => 'jm'.hashCode,
3 => 'hitomi'.hashCode,
4 => 'wnacg'.hashCode,
6 => 'nhentai'.hashCode,
_ => comic['type']
},
"id": comic['target'],
"maxPage": comic["max_page"],
"ep": comic["ep"],
"page": comic["page"],
"time": comic["time"],
"title": comic["title"],
"subtitle": comic["subtitle"],
"cover": comic["cover"],
}),
);
}
}
catch(e) {
Log.error("Import Data", "Failed to import history: $e");
}
finally {
db.dispose();
}
}
} finally {
cacheDir.deleteIgnoreError(recursive: true);
}
} }

View File

@@ -265,7 +265,9 @@ Future<FileSelectResult?> selectFile({required List<String> ext}) async {
file = FileSelectResult(xFile.path); file = FileSelectResult(xFile.path);
} }
if (!ext.contains(file.path.split(".").last)) { if (!ext.contains(file.path.split(".").last)) {
App.rootContext.showMessage(message: "Invalid file type"); App.rootContext.showMessage(
message: "Invalid file type: ${file.path.split(".").last}",
);
return null; return null;
} }
return file; return file;