From db11338e032f67a715f681a8bd43e14c6aba0c6a Mon Sep 17 00:00:00 2001 From: Vito Sansevero Date: Mon, 26 Oct 2026 17:55:16 -0700 Subject: [PATCH] docs(lora): describe how the import finds LoraManager's files (#355) --- README.md | 8 ++++++-- TESTING.md | 30 ++++++++++++++++++++++++++++-- 2 files changed, 34 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index e59a5e88..67a26985 100644 --- a/README.md +++ b/README.md @@ -483,11 +483,15 @@ If you use [ComfyUI-Lora-Manager](https://github.com/willmiao/ComfyUI-Lora-Manag Click **Import LoRA Data** in the settings panel to start the import. A progress popup shows real-time status as each LoRA is processed: -- Scans all LoRA directories (including `extra_model_paths.yaml` paths) for metadata -- Downloads example images from CivitAI as 512px thumbnails +- Reads LoRA Manager's own settings the way LoRA Manager does: from the folder in `LORA_MANAGER_SETTINGS_DIR`, from the plugin's `settings.json` in portable mode, or from your user config folder, and only the keys that say where its files are +- Finds each LoRA's metadata in both storage modes: beside the model (the default) or in the central sidecar folder, and imports only LoRAs whose model file still exists in a LoRA folder (the review says how many metadata files it skipped) +- Links LoRA Manager's preview (including `.preview.webp` and video previews) and every downloaded example image and video where they are, without copying them +- Downloads example images from CivitAI as 512px thumbnails only for LoRAs that have no local image - Creates a prompt entry for each LoRA with trigger words, example prompts, and preview images - All imported LoRAs are tagged with `lora-manager` category for easy filtering +The System › Integrations review names the settings it read (source, storage mode and LoRA Manager library) and counts metadata files, LoRAs and LoRAs with local images. If LoRA Manager's settings cannot be used, it says why and nothing is changed. + ![LoRA Results](images/pm-lora-filtered.png) After import, filter by the `lora-manager` category to browse your LoRA collection. diff --git a/TESTING.md b/TESTING.md index 3d26c39e..f43da6d4 100644 --- a/TESTING.md +++ b/TESTING.md @@ -3410,14 +3410,40 @@ refused while a restore runs; the review is a request lease ("LoRA import review accepts the optional `expected_revision`. LoraManager detection also searches every `custom_nodes` folder ComfyUI registers through `folder_paths` (#144), main folder first. +**Where LoraManager keeps its files (#355).** `py/lora_manager_layout.py` repeats +LoraManager's rules without importing it (`tests/test_lora_manager_layout.py`). The +settings file is `/settings.json`, else the plugin's own +`settings.json` when portable mode is on (`LORA_MANAGER_PORTABLE` `1`/`0` decides, other +values are ignored; otherwise the JSON value `use_portable_settings: true`), else +`platformdirs.user_config_dir("ComfyUI-LoRA-Manager")`. It is read as UTF-8, at most 5 MB, +and only seven keys are kept (`SETTINGS_KEYS`); a missing file means LoraManager's +defaults. Discovery: in `alongside` mode every LoRA root is searched and a sidecar is kept +when `.safetensors` exists beside it; in `centralized` mode only the sidecar root is +searched and a sidecar is kept when its `file_path` exists inside a LoRA root (unparseable +ones are skipped by name). `lora_files` counts the metadata files seen, `with_metadata` +the kept, readable LoRAs and `skipped` the rest. Media per LoRA, without repeats: the +preview (`preview_url`, else LoraManager's `PREVIEW_EXTENSIONS` order), then every file in +`[/]//` in natural order; a leading video yields to the +first still. A file counts only with a servable extension and inside the guarded media +roots. CivitAI downloads run only for a LoRA without local media. The folder guard keeps a +settings folder only when it exists and is neither a filesystem root (`/`, `C:\`, a UNC +share root) nor the home folder or one of its ancestors (realpath + `normcase`). An +unusable layout (no install, unreadable / non-JSON / non-object / oversized settings, no +`platformdirs`, a missing or refused centralized sidecar root) gives a review without a +token ("LoraManager settings: not usable: . Nothing was changed."), a legacy scan +error with that reason, the default LoRA roots for serving, and trigger words from the +default roots in alongside mode. `tests/run_suite.py` and `tests/browser/server.py` point +`LORA_MANAGER_SETTINGS_DIR` at a disposable folder, so no test reads the developer's real +LoraManager settings; tests that call `load_layout` inject their own folder too. + `tests/browser/workspace_integrations_fixture.py` (`/__test__/integrations/*`) makes a fake LoraManager install and LoRA folder under the server's temp root, holds or fails the import, saves a blocking pair and answers CivitAI downloads with a stub opener, so no test reaches the network. ```sh -python3 -m unittest tests.test_lora_import tests.test_api_lora tests.test_lora_database \ - tests.test_lora_utils -v +python3 -m unittest tests.test_lora_manager_layout tests.test_lora_import tests.test_api_lora \ + tests.test_lora_database tests.test_lora_utils -v node --test tests/js/workspace-system-integrations.test.js tests/js/prompt-bridge-adapter.test.js npm run --prefix tools/vendor test:workflows -- workspace-system-integrations.spec.mjs \ system-integrations-concept.spec.mjs \