feat: store packaged user data under data directory
This commit is contained in:
+115
-1
@@ -18,7 +18,13 @@ class AppConfigTests(TempDirMixin, unittest.TestCase):
|
||||
|
||||
config = appconfig.load_config(config_path)
|
||||
self.assertTrue(os.path.exists(config_path))
|
||||
self.assertEqual("images", appconfig.image_dir(config))
|
||||
self.assertEqual(os.path.join(temp_dir, "images"), appconfig.image_dir(config))
|
||||
self.assertEqual(os.path.join(temp_dir, "chrome_user_data_dir"), appconfig.user_data_root(config))
|
||||
self.assertEqual(os.path.join(temp_dir, "cmshopee.db"), appconfig.db_path(config))
|
||||
self.assertEqual(temp_dir, appconfig.data_dir(config))
|
||||
self.assertEqual(config_path, config["config_path"])
|
||||
self.assertEqual(os.path.join(temp_dir, "config", "ai_models.json"), config["ai_models_path"])
|
||||
self.assertEqual(os.path.join(temp_dir, "config", "cmhub.json"), config["cmhub_config_path"])
|
||||
self.assertEqual(240, appconfig.response_timeout(config))
|
||||
self.assertFalse(appconfig.ai_config(config)["generate_cover"])
|
||||
|
||||
@@ -31,6 +37,114 @@ class AppConfigTests(TempDirMixin, unittest.TestCase):
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_config_save_does_not_persist_runtime_paths(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
config_path = os.path.join(temp_dir, "config.json")
|
||||
|
||||
saved = appconfig.save_config(
|
||||
{
|
||||
"data_dir": os.path.join(temp_dir, "data"),
|
||||
"config_path": "runtime-only",
|
||||
"ai_models_path": "runtime-only",
|
||||
"cmhub_config_path": "runtime-only",
|
||||
"image_dir": "images",
|
||||
},
|
||||
path=config_path,
|
||||
)
|
||||
|
||||
self.assertEqual(temp_dir, saved["data_dir"])
|
||||
with open(config_path, "r", encoding="utf-8") as fh:
|
||||
persisted = json.load(fh)
|
||||
self.assertNotIn("data_dir", persisted)
|
||||
self.assertNotIn("config_path", persisted)
|
||||
self.assertNotIn("ai_models_path", persisted)
|
||||
self.assertNotIn("cmhub_config_path", persisted)
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_data_paths_resolve_under_default_data_dir(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
data_root = os.path.join(temp_dir, "data")
|
||||
cfg = {
|
||||
"data_dir": data_root,
|
||||
"user_data_root": "chrome_user_data_dir",
|
||||
"image_dir": "images",
|
||||
"db_path": "cmshopee.db",
|
||||
}
|
||||
|
||||
self.assertEqual(os.path.join(data_root, "chrome_user_data_dir"), appconfig.user_data_root(cfg))
|
||||
self.assertEqual(os.path.join(data_root, "images"), appconfig.image_dir(cfg))
|
||||
self.assertEqual(os.path.join(data_root, "cmshopee.db"), appconfig.db_path(cfg))
|
||||
self.assertEqual(os.path.join(data_root, "title_prompt.txt"), appconfig.title_prompt_path(cfg))
|
||||
self.assertEqual(os.path.join(data_root, "prompts", "cover"), appconfig.cover_prompts_dir(cfg))
|
||||
self.assertEqual(os.path.join(data_root, "logs"), appconfig.diagnostic_log_dir(cfg))
|
||||
|
||||
portable = dict(cfg)
|
||||
portable["db_path"] = os.path.join("data", "cmshopee.db")
|
||||
self.assertEqual(os.path.join(data_root, "cmshopee.db"), appconfig.db_path(portable))
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_prepare_data_dir_migrates_legacy_layout(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
with open(os.path.join(temp_dir, "config.json"), "w", encoding="utf-8") as fh:
|
||||
fh.write("{}")
|
||||
with open(os.path.join(temp_dir, "cmshopee.db"), "w", encoding="utf-8") as fh:
|
||||
fh.write("db")
|
||||
os.makedirs(os.path.join(temp_dir, "images"), exist_ok=True)
|
||||
with open(os.path.join(temp_dir, "images", "cover.jpg"), "w", encoding="utf-8") as fh:
|
||||
fh.write("image")
|
||||
os.makedirs(os.path.join(temp_dir, "config"), exist_ok=True)
|
||||
with open(os.path.join(temp_dir, "config", "cmhub.json"), "w", encoding="utf-8") as fh:
|
||||
fh.write("{}")
|
||||
|
||||
data_root = os.path.join(temp_dir, "data")
|
||||
prepared = appconfig.prepare_data_dir(base_dir=temp_dir, data_dir_path=data_root)
|
||||
|
||||
self.assertEqual(data_root, prepared)
|
||||
self.assertTrue(os.path.exists(os.path.join(data_root, "config.json")))
|
||||
self.assertTrue(os.path.exists(os.path.join(data_root, "cmshopee.db")))
|
||||
self.assertTrue(os.path.exists(os.path.join(data_root, "images", "cover.jpg")))
|
||||
self.assertTrue(os.path.exists(os.path.join(data_root, "config", "cmhub.json")))
|
||||
self.assertFalse(os.path.exists(os.path.join(temp_dir, "config.json")))
|
||||
self.assertFalse(os.path.exists(os.path.join(temp_dir, "images")))
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_prepare_data_dir_blocks_conflicting_migration(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
with open(os.path.join(temp_dir, "config.json"), "w", encoding="utf-8") as fh:
|
||||
fh.write("{}")
|
||||
data_root = os.path.join(temp_dir, "data")
|
||||
os.makedirs(data_root, exist_ok=True)
|
||||
with open(os.path.join(data_root, "config.json"), "w", encoding="utf-8") as fh:
|
||||
fh.write("{}")
|
||||
|
||||
with self.assertRaises(appconfig.DataMigrationConflictError) as ctx:
|
||||
appconfig.prepare_data_dir(base_dir=temp_dir, data_dir_path=data_root)
|
||||
|
||||
self.assertIn("无法自动迁移", str(ctx.exception))
|
||||
self.assertTrue(os.path.exists(os.path.join(temp_dir, "config.json")))
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_prepare_data_dir_reports_unwritable_path(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
data_root = os.path.join(temp_dir, "data")
|
||||
with open(data_root, "w", encoding="utf-8") as fh:
|
||||
fh.write("not a directory")
|
||||
|
||||
with self.assertRaises(appconfig.DataDirectoryWriteError) as ctx:
|
||||
appconfig.prepare_data_dir(
|
||||
base_dir=temp_dir,
|
||||
data_dir_path=data_root,
|
||||
migrate=False,
|
||||
)
|
||||
|
||||
self.assertIn("数据目录不可写", str(ctx.exception))
|
||||
|
||||
self.assert_removed(temp_dir)
|
||||
|
||||
def test_cmhub_defaults_old_config_and_key_helper(self):
|
||||
with self.make_temp_dir() as temp_dir:
|
||||
config_path = os.path.join(temp_dir, "config.json")
|
||||
|
||||
Reference in New Issue
Block a user