27 Commits

Author SHA1 Message Date
pax
90b27fe36a info_panel: render uncategorized tags under Other bucket
behavior change: tags that weren't in any section of
post.tag_categories (partial batch-API response, HTML scrape
returned empty, stale cache) used to silently disappear from the
info panel — the categorized loop only iterated categories, so
any tag without a cached label just didn't render.

Now after the known category sections, any remaining tags from
post.tag_list are collected into an 'Other:' section with a
neutral header. The tag is visible and clickable even when its
type code never made it into the cache.

Reported against Gelbooru posts with long character tag names
where the batch tag API was returning partial results and the
missing tags were just gone from the UI.
2026-04-15 17:42:38 -05:00
pax
730b2a7b7e settings: add Clear Tag Category Cache button
behavior change: Settings > Cache now has a 'Clear Tag Category
Cache' action that wipes the per-site tag_types table via the
existing db.clear_tag_cache() hook. This also drops the
__batch_api_probe__ sentinel so Gelbooru/Moebooru sites re-probe
the batch tag API on next use and repopulate the cache from a
fresh response.

Use case: category types like Character/Copyright/Meta appear
missing when the local tag cache was populated by an older build
that didn't map all of Gelbooru's type codes. Clearing lets the
current _GELBOORU_TYPE_MAP re-label tags cleanly instead of
inheriting whatever the old rows said.
2026-04-15 17:39:57 -05:00
pax
0f26475f52 detect: remove leftover if-True indent marker
Dead syntax left over from a prior refactor. No behavior change.
2026-04-15 17:34:27 -05:00
pax
cf8bc0ad89 library_save: require category_fetcher to prevent silent category drop
behavior change: save_post_file's category_fetcher argument is now
keyword-only with no default, so every call site has to pass something
explicit (fetcher instance or None). Previously the =None default let
bookmark→library save and bookmark Save As slip through without a
fetcher at all, silently rendering %artist%/%character% tokens as
empty strings and producing filenames like '_12345.jpg' instead of
'greatartist_12345.jpg'.

BookmarksView now takes a category_fetcher_factory callable in its
constructor (wired to BooruApp._get_category_fetcher), called at save
time so it picks up the fetcher for whatever site is currently active.

tests/core/test_library_save.py pins the signature shape and the
three relevant paths: fetcher populates empty categories, None
accepted when categories are pre-populated (Danbooru/e621 inline),
fetcher skipped when template has no category tokens.
2026-04-15 17:32:25 -05:00
pax
bbf0d3107b category_fetcher: stop flipping _batch_api_works=False on transient errors in single-post path
behavior change: a single mid-call network drop could previously
poison _batch_api_works=False for the whole site, forcing every
future ensure_categories onto the slower HTML scrape path. _do_ensure
now routes the unprobed case through _probe_batch_api, which only
flips the flag on a clean HTTP 200 with zero matching names; timeout
and non-200 responses leave the flag None so the next call retries
the probe.

The bug surfaced because fetch_via_tag_api swallows per-chunk
failures with 'except Exception: continue', so the previous code
path couldn't distinguish 'API returned zero matches' from 'the
network dropped halfway through.' _probe_batch_api already made
that distinction for prefetch_batch; _do_ensure now reuses it.

Tests in tests/core/api/test_category_fetcher.py pin the three
routes (transient raise, clean-200-zero-matches, non-200).
2026-04-15 17:29:01 -05:00
pax
ec9e44efbe category_fetcher: extract shared tag-API params builder
Both fetch_via_tag_api and _probe_batch_api built the same params
dict (with identical lstrip/startswith credential quirks) inline.
Pulled into _build_tag_api_params so future credential-format tweaks
have one site, not two.
2026-04-15 17:27:10 -05:00
pax
24f398795b changelog: drag-start threshold bump 2026-04-14 23:27:32 -05:00
pax
21bb3aa979 CHANGELOG: add [Unreleased] section for changes since v0.2.7 2026-04-14 19:05:23 -05:00
pax
289e4c2fdb release: v0.2.7 2026-04-14 19:03:22 -05:00
pax
a2609199bd changelog: tiled grid repaint + video thumb 10% seek 2026-04-14 15:58:36 -05:00
pax
70a7903f85 changelog: VRAM fixes and popout open animation 2026-04-13 21:49:38 -05:00
pax
0d75b8a3c8 changelog: 9 commits since last Unreleased update
Fixed: GL context leak on Mesa/Intel, popout teardown None guards,
category_fetcher XXE/billion-laughs rejection.
Changed: dark Fusion palette fallback, popout aspect refit on untile
(behavior change).
Removed: rolled in latest dead-var and unused-import cleanups.
2026-04-13 19:02:40 -05:00
pax
11cc26479b changelog: parallel video caching, mpv library thumbnails 2026-04-12 14:31:33 -05:00
pax
445d3c7a0f CHANGELOG: add [Unreleased] section for changes since v0.2.6 2026-04-12 07:23:46 -05:00
pax
1531db27b7 update changelog to v0.2.6 2026-04-11 16:41:37 -05:00
pax
ec781141b3 docs: changelog entry for 2026-04-10 security audit batch
Adds an [Unreleased] Security section listing the 12 fixed findings
(2 High, 4 Medium, 4 Low, 2 Informational), the 4 skipped
Informational items with reasons, and the user-facing behavior
changes.

Audit-Ref: SECURITY_AUDIT.md (full batch)
2026-04-11 16:27:50 -05:00
pax
a90aa2dc77 rebuild CHANGELOG.md from Gitea release bodies 2026-04-10 21:53:16 -05:00
pax
5bf85f223b add v prefix to version strings 2026-04-10 21:25:27 -05:00
pax
5e6361c31b release 0.2.5 2026-04-10 21:17:10 -05:00
pax
bda21a2615 changelog: update v0.2.4 with tag category, bug fix, and UI changes 2026-04-09 23:12:22 -05:00
pax
272a84a0ab Update CHANGELOG.md 2026-04-10 02:20:19 +00:00
pax
3a87d24631 Update CHANGELOG.md 2026-04-10 02:09:01 +00:00
pax
fa06eb16be Update CHANGELOG.md 2026-04-10 02:05:30 +00:00
pax
09485884de pre-release v0.2.4 2026-04-09 21:03:36 -05:00
pax
23828e7d0c Release 0.2.3 2026-04-09 00:10:22 -05:00
pax
56cb5ce1df Scroll tilt navigates one cell/post in grid, preview, and popout 2026-04-07 08:50:13 -05:00
pax
2fbf2f6472 0.2.0: mpv backend, popout viewer, preview toolbar, API retry, SearchState refactor
Video:
- Replace Qt Multimedia with mpv via python-mpv + OpenGL render API
- Hardware-accelerated decoding, frame-accurate seeking, proper EOF detection
- Translucent overlay controls in both preview and popout
- LC_NUMERIC=C for mpv locale compatibility

Popout viewer (renamed from slideshow):
- Floating toolbar + controls overlay with auto-hide (2s)
- Window auto-resizes to content aspect ratio on navigation
- Hyprland: hyprctl resizewindowpixel + keep_aspect_ratio prop
- Window geometry persisted to DB across sessions
- Smart F11 exit sizing (60% monitor, centered)

Preview toolbar:
- Bookmark, Save, BL Tag, BL Post, Popout buttons above preview
- Save opens folder picker menu, shows Save/Unsave state
- Blacklist actions have confirmation dialogs
- Per-tab button visibility (Library: Save + Popout only)
- Cross-tab state management with grid selection clearing

Search & pagination:
- SearchState dataclass replaces 8 scattered attrs + defensive getattr
- Media type filter dropdown (All/Animated/Video/GIF/Audio)
- API retry with backoff on 429/503/timeout
- Infinite scroll dedup fix (local seen set per backfill round)
- Prev/Next buttons hide at boundaries, "(end)" status indicator

Grid:
- Rubber band drag selection
- Saved/bookmarked dots update instantly across all tabs
- Library/bookmarks emit signals on file deletion for cross-tab sync

Settings & misc:
- Default site option
- Max thumbnail cache setting (500MB default)
- Source URLs clickable in info panel
- Long URLs truncated to prevent splitter blowout
- Bulk save no longer auto-bookmarks
2026-04-06 13:43:46 -05:00