- Move the read-only OpenAPI compat surface from /api/v2/assets to
/mjr/am/compat/assets so it never squats ComfyUI core's /api namespace;
the legacy alias is opt-in via MJR_AM_LEGACY_API_V2_ASSETS=1.
- Allow Python 3.14 (requires-python <3.15) and add 3.14 to CI and tox.
- Stop wrapping api.queuePrompt: progress tracking now resolves the
running prompt from the core Jobs API (getJobDetail), then /queue and
/history, driven by websocket events. Remove wrapHostQueuePrompt.
- Add opt-in Majoor.Integration.HideNativeAssetsTab setting that hides
ComfyUI's native Assets sidebar tab through the official
getSidebarTabs/unregisterSidebarTab API and restores it when disabled.
- Fix all 913 type errors in tsconfig.test.json and type-check tests in
CI; drop a duplicated `stubs` key in asset_card_inner test; make
addToastHistory's type argument optional for the object form.
- Update audit report, changelog, API reference and env var docs.
- Sidebar prewarm no longer steals the Vue host from an already-open panel:
mountKeepAlive only attaches on first creation unless explicitly allowed,
and teardown resets the prewarm state and removes its detached container.
- Topbar MFV button now also observes the actionbar container's parent so a
full replacement of .actionbar-container (not just mutations inside it) is
detected and the button is remounted.
- get() skips request deduplication when a caller passes its own AbortSignal,
since the shared fetch only ever wired up the first caller's signal.
- The API client now rejects response envelopes missing a boolean `ok` field
(including bare arrays) and downgrades ok:true responses paired with an
HTTP error status to INVALID_RESPONSE.
- frontend-compat-nightly.yml: upstream ComfyUI_frontend's build:types now
emits per-file declarations mirroring src/ instead of one bundled file, so
the previous entrypoint paths no longer exist. The activation step now also
checks dist/src/types/index.d.ts and copies the whole dist/ tree so the
unbundled declaration's relative imports keep resolving.
- Require the same Comfy auth on all Majoor GET routes as on writes, closing
a read-confidentiality gap for remote/multi-user deployments (no-op when
Comfy auth is disabled, the default single-user setup).
- Gate nightly and stable releases on a quality job (pytest, mypy, frontend
typecheck/build/tests, dist/ drift check) before publishing, and refresh
the committed dist/ bundle to match a clean build.
- Pin softprops/action-gh-release and Comfy-Org/publish-node-action to
commit SHAs.
- Resolve ComfyUI's CacheProvider through the public comfy_api.latest.Caching
alias instead of the underscore-private _caching module.
- Make asset-delete DB cleanup atomic: a failed cleanup statement now aborts
the transaction instead of committing a partial delete.
Security
--------
ComfyUI's PromptServer.add_routes() mirrors every registered route under a
second "/api" prefix, so /mjr/am/<mutation> is also served at
/api/mjr/am/<mutation>. The auth middleware matched only the canonical
prefix, so the mirrored path reached the same handler with the
authentication check skipped entirely, and without the hardening headers:
POST /mjr/am/assets/delete -> requires_auth = True
POST /api/mjr/am/assets/delete -> requires_auth = False
Replaced the prefix test with a shared _is_majoor_path() boundary covering
the canonical prefixes, ComfyUI's /api mirror, and the /api/v2/assets
compat surface. Verified it does not capture ComfyUI's own routes. CSRF,
rate limiting and safe-mode gates are per-handler and were unaffected.
Licensing
---------
PrimeVue 5 is no longer MIT: PrimeTek moved it to the commercial "PrimeUI"
license, which requires a key, shows a license notice without one, and
forbids redistributing it "as a component library or development tool"
without a separate OEM License. Dependabot had auto-merged 4.5.5 -> 5.0.1.
This project is GPL-3.0 and commits dist/ to the repo, so shipping it would
nag every user and conflict with the GPL's redistribution requirement.
Pinned back to 4.5.5 (last MIT release). The 5.x bump had touched only
package.json/package-lock.json, so no source depended on v5 APIs. The
revert drops @primeui/license-manager and its @noble/ed25519 key-signature
stack; the primevue chunk shrinks 555.70 -> 520.61 kB. Dependabot is now
configured to ignore primevue major bumps.
Correctness
-----------
- api_v2_assets: stop returning the DB's absolute filepath on this
network-reachable surface; subfolder + root_id already convey location
without disclosing local disk layout.
- watcher: enforce _RECENT_GENERATED_HARD_CAP after inserting a batch;
pruning only beforehand let a large batch overshoot the cap.
- routes/registry: track registered route groups individually so a group
failing part-way through does not re-register earlier groups on retry.
- fs_walker/scanner: apply the viewer's root check to symlinked files, so
the scanner stops indexing symlinks whose target escapes every allowed
root ("ghost assets" the viewer then refuses to open). Consulted only for
actual symlinks, so ordinary scans pay no extra I/O.
- routes/registry_app: skip the redundant app.add_routes() on the live
PromptServer app; ComfyUI adds the shared table itself after node
loading, so every core and Majoor route was registered twice at startup.
- Result: unwrap()/unwrap_or()/map() gated on `data is not None`, treating
a legitimate Ok(None) as failure; gate on `ok` instead.
- custom_roots: replace a leftover debug print() that wrote user file paths
to stderr on every move request with logger.debug.
- schema: drop the redundant UNIQUE(filepath, source, root_id) index
(migration m022). assets.filepath is already UNIQUE, so it could never
reject a row the column constraint does not, nor narrow a lookup - it
only cost a second B-tree write per asset on the scan hot path.
Frontend
--------
- entry.ts: app.registerExtension() throws on a duplicate name and ComfyUI
exposes no unregisterExtension, so a live re-import threw before setup()
ran and the reload-safe teardown never executed. Catch it and re-run
setup() directly.
- Rebuilt dist/ so both the reload fix and the PrimeVue revert ship.
CI / tooling
------------
- frontend-compat-nightly: the types step died with a bare "cp: cannot
stat" (upstream's build has not emitted dist/index.d.ts since Aug 26).
Check both candidate paths and dump dist/ with an actionable message.
- package.json: lenient checks that swallowed their exit code are now
suffixed :advisory, the plain names are strict, and quality:strict runs
the full set.
Verified: 1841 Python tests pass (5 skipped, symlink privileges), ruff
clean; tsc --noEmit clean, 831 JS tests pass, eslint clean, build succeeds.
- Add keyboard shortcuts for video in-point (I), out-point (O), and navigation (Home/End)
- Implement swipe gesture for navigating between assets in the viewer
- Add option to copy prompt to clipboard (Ctrl/Cmd+C)
- Improve stack group card functionality and representative selection
- Optimize image preloading for smoother navigation
- Enhance audio visualizer with WebGL support and mode switching
- Refine feed card appearance and interaction
- Introduced runtime bootstrap helpers in `mjr_am_backend.features.runtime` for dependency initialization.
- Implemented `apply_startup_settings` to handle various startup configurations.
- Added search request normalization helpers in `mjr_am_backend.features.search` including `SearchRequestContext` and `parse_search_request` for better query handling.
- Created audit logging helpers in `mjr_am_backend.routes.core.audit_log` for state-changing route handlers.
- Developed a quality gate script in `scripts/run_quality_gate.py` to enforce code quality checks.
- Added comprehensive tests for audit routes, scan consistency, vendor routes, and code quality metrics.
- Added support for fetching nightly release markers and checking for updates.
- Introduced a notice for AI features in local builds.
- Improved version badge display logic in the header view.
- Refactored caption normalization logic in vector indexing.
- Enhanced floating viewer with edge resizing capabilities.
- Updated styles for pop-in mode and resizing state.
- Added tests for enhanced prompt generation and X-CLIP embedding handling.