Корзини бібліотеки і архіву¶
BamDude має дві незалежні корзини, щоб видалення ніколи мовчки не знищувало дані:
- Корзина бібліотеки — для файлів, які ти завантажив або сляйснув у бібліотеку. Має opt-in авто-purge, що переносить idle-файли в корзину по 24г drift-розкладу.
- Корзина архіву — для рядків архіву, які ти (або "Empty trash" sweeps) явно видалив. З 0.4.2 manual-only — більше немає щоденного auto-purge, що переносив старі archive-рядки сюди.
Обидві корзини одного крою: soft-delete на ручне видалення, конфігурований restore-window, scheduled-retention sweeper що hard-delete'ить усе після вікна, і chain-of-custody guard, що відмовляється hard-delete'ити байти бібліотеки, якщо на них ще посилається активний архів.
Чому archive auto-purge видалили в 0.4.2
Upstream-портований archive auto-purge запускався щодня і переносив будь-який archive-рядок старший за поріг у корзину. У BamDude post-b1 це виявилося і редундантним (per-design 3MF Auto-Cleanup вже звільняє диск для холодних дизайнів, зберігаючи історію), і шкідливим (per-row aging означало, що модель, яку друкують щотижня два роки, втрачала найраніші ~70 archive-рядків поодинці, навіть коли дизайн ще hot — мовчки знищуючи print-історію, заради якої BamDude і існує). Ручний flow delete → trash → restore → empty-trash лишається інтактним для явного видалення рядків; зник лише щоденний auto-purge sweep.
Як працює soft-delete¶
Коли ти видаляєш файл бібліотеки чи архів (вручну або через auto-purge):
- У ряду виставляється
deleted_at = now()— він пропадає з основного списку і дедуп-запитів. - Байти + мініатюри лишаються на диску.
- Сторінка корзини (admin-секція в Settings + окремі маршрути
/files/trashі/archives/trash) показує кожен рядок з countdown'ом до hard-delete. - Restore — повертає
deleted_at = NULL, рядок з'являється знову, мов і не видаляли. - Hard-delete now — стирає рядок + байти миттєво (admin only).
- Після retention-вікна фоновий sweeper hard-delete'ить усе, що проіснувало в корзині довше за поріг.
Reference-aware hard-delete¶
На файли бібліотеки можуть посилатися рядки архіву (кожен друк файлу породжує архів). Якщо hard-delete'нути байти бібліотеки, на які ще посилається активний (non-trashed) архів — ламається chain-of-custody: реприни з того архіву не матимуть що відсилати.
BamDude таке відмовляє з 409 Conflict і структурованою payload'ою:
UI показує: Pinned by 3 active archives — delete those first or trash them too. Bulk-операція Empty trash пропускає pinned-файли і повідомляє кількість окремо, тож зрозуміло, чому деякі не видалились.
Sweeper корзини бібліотеки застосовує той же гейт у час retention: рядок, що вже за вікном, лишається pinned і чекає наступного тіку, якщо архіви на нього ще посилаються. Як тільки ті архіви теж потраплять у корзину — файл стає eligible на наступному тіку.
Налаштування¶
Settings → Printing → File Manager має два блоки один під одним (спершу auto-purge, ретеншн корзини знизу — той самий порядок, що й в Archive Settings):
Auto-purge бібліотеки¶
Розгорнуті контроли ховаються, коли тоглер вимкнено; увімкни його, щоб їх побачити.
| Опція | За замовчуванням | Що контролює |
|---|---|---|
| Auto-purge enabled | off | Master-тоглер drift-режиму purge, який переносить залежані файли бібліотеки в корзину. Гейтить лише 15-хвилинний авто-тік — ручний /library/purge працює завжди. |
| Auto-purge age | 90 днів | Файли idle (без свіжого друку, без свіжого редагування) довше за це стають кандидатами на auto-purge. |
| Include never-printed | off | Якщо on — never-printed-файли теж рахуються до threshold'у. Якщо off — auto-purge зачіпає лише друковані файли (захищає те, що ти залив, але ще не друкував). |
| Картки Last / Next run (0.4.2) | — | Той самий спільний компонент <LastNextRunCards>, що й у 3MF-очищенні архіву. Показує «перенесено 5 файлів у корзину, 4 години тому» + «через ~20 годин». Після рестарту сервера лічильник moved втрачається, і картка пише «лічильник втрачено при рестарті — дивись логи» замість 0 (персистентна мітка library_auto_purge_last_run переживає рестарт, губиться лише число). |
Ретеншн корзини бібліотеки¶
| Опція | За замовчуванням | Що контролює |
|---|---|---|
| Trash retention | 30 днів | Скільки soft-deleted файл сидить у корзині перед hard-delete sweeper'ом. Діапазон 1–365 днів. Sweeper ретеншну ходить кожні 15 хв — та сама каденція, що й раніше. |
Ретеншн корзини архіву¶
Auto-purge для архівів прибрано у 0.4.2 (див. примітку вгорі сторінки). Лишився тільки sweeper ретеншну корзини:
| Опція | За замовчуванням | Що контролює |
|---|---|---|
| Trash retention | 30 днів | Скільки soft-deleted архів сидить у корзині перед hard-delete sweeper'ом. Діапазон 1–365 днів. Sweeper так само ходить кожні 15 хв. |
Форма розкладу (обидві корзини)¶
| Механізм | Каденція | Що скидає |
|---|---|---|
| Auto-purge бібліотеки | тік 15 хв → запуск, коли now - last_run >= 24 год |
і авто-тік, і ручний /library/purge штампують library_auto_purge_last_run |
| 3MF-очищення архіву | тік 15 хв → запуск, коли now - last_run >= 24 год |
і авто-тік, і ручний /archives/cleanup/run штампують archive_3mf_cleanup_last_run |
| Sweeper ретеншну корзини (обидві) | тік 15 хв → hard-delete всього, що вийшло за вікно | — |
Затримка першого спрацювання (auto-purge / cleanup): цикл спить 15 хв перед першою перевіркою, тож увімкнений зараз тоглер дасть перший авто-запуск приблизно через 15 хв (мітки last-run ще немає, тому 24-годинний гейт на першому тіку не діє). Кнопка «Run now» запускає негайно — ручний запуск штампує ту саму мітку last_run і починає 24-годинний drift-цикл.
Дозволи¶
| Permission | Що дозволяє |
|---|---|
library:delete_own / library:delete_all |
Soft-delete (move to trash). Той самий permission, що гейтує звичайну delete-кнопку — якщо можеш видалити, можеш і відновити. |
archives:delete_own / archives:delete_all |
Те саме, для архівів. |
library:purge |
Тригерити admin-purge + змінювати налаштування корзини бібліотеки. |
archives:purge |
Тригерити admin-purge + змінювати налаштування корзини архіву. |
Manual hard-delete зі сторінки корзини теж потребує відповідного library:purge / archives:purge.
Restore / Empty / Hard-delete¶
Обидві сторінки корзини підтримують:
- Restore — повернути
deleted_at = NULL. Рядок з'являється у списку. - Hard-delete now — admin-only. Стирає рядок + байти миттєво, обходить retention.
- Empty trash — bulk hard-delete усього, що вже eligible. Пропускає pinned (бібліотека) і повідомляє
{deleted, skipped_pinned}, щоб UI пояснив розрив. - Multi-select — bulk Restore і bulk Hard-delete на обраних рядках.
Відновлення файла бібліотеки питає, перш ніж створити дубль
Усі інші шляхи тепер відмовляються зберігати той самий файл двічі, тож дістати його з кошика — єдиний спосіб, що лишився, отримати два однакові файли. Відновлення спершу перевіряє й озивається лише якщо файл справді побайтово збігається з тим, що у вас уже є — діалог називає наявний файл, а рішення за вами.
Відновлення кількох одразу питає один раз, перелічуючи, які саме з них дублі, і пропонує відновити лише решту. Файл, до якого нічого не збігається, відновлюється як раніше, без питань.
Воно питає, а не відмовляє. Дубль може бути навмисним — два профілі MakerWorld можуть дати побайтово однакові 3MF — і саме та людина, яка поклала файл у кошик, зараз його звідти й дістає.
Кошик архівів до 0.5.4 насправді нічого не видаляв
«Очистити кошик» повідомляв видалено 0 і не прибирав нічого взагалі; Видалити назавжди на одному архіві віддавало помилку; а сміттяр ретенції зносив рядки з бази, лишаючи на диску кожен 3MF, прев'ю, таймлапс і фото. Полагоджено у 0.5.4 — але файли, що натекли до того, лишаються на диску, і BamDude не піде видаляти їх без запиту. scripts/prune_orphan_archive_files.py показує, на що більше немає посилань, і видаляє лише з --apply.
Дедуп ігнорує trashed-рядки¶
Кожен дедуп-запит у BamDude — перевірка при upload'і, бейдж "X duplicates" у списку, панель "Find similar" в file-detail, anchor find_existing_archive в archive-chain — фільтрує trashed-рядки. Trashed-сибл ніколи не treat'иться як source-of-truth: видалення файлу з корзини раптом не роздуває counter'и інших файлів; повторний upload trashed-файлу імпортується чисто, замість silently link'нутись на приречений рядок.
Зовнішні папки оминають корзину¶
Зовнішні папки бібліотеки (mounted NAS-шари, USB-диски) не йдуть через корзину — їхні байти живуть поза контролем BamDude, тож відновлювати нічого. Видалення external-запису просто стирає DB-рядок + мініатюру; сам файл на mount'і не зачіпається.
Bulk-операція Empty trash і per-row Hard-delete now ніколи не торкаються external-папок.
Дивись також¶
- File Manager — де живе кнопка Trash + кнопка Purge old.
- Print Archiving — керування корзиною архіву поряд із заголовком архіву.
- Authentication — як
library:purge/archives:purgeприв'язані до дефолтних груп.