Skip to content

Expose authenticated model coverage and application version APIs - #906

Open
rendyhd wants to merge 7 commits into
NeptuneHub:mainfrom
rendyhd:codex/recording-search-status
Open

rendyhd wants to merge 7 commits into
NeptuneHub:mainfrom
rendyhd:codex/recording-search-status

Conversation

@rendyhd

@rendyhd rendyhd commented Sep 12, 2026

Copy link
Copy Markdown
Contributor

AS-IS

Ordinary clients cannot read numeric coverage for all models. The setup wizard exposes admin-only visual bands, and application version reporting is not available through a dedicated authenticated route.

TO-BE

Adds two endpoints available to ordinary authenticated users and bearer-token clients:

  • GET /api/models: effective enablement and global coverage for MusiCNN (musicnn), DCLAP (clap), Lyrics (lyrics), and Neural Fingerprint (neural-fingerprint). Each coverage object contains count, total, and percentage.
  • GET /api/models?server_id=<id-or-name> (also server=): keeps global coverage and adds local coverage for the resolved server. Without a server parameter, local coverage and server_id are omitted.
  • GET /api/version in app.py: returns only the effective app_version, including release suffixes.

Model coverage contains no API/application version or recording-limit fields. MusiCNN is always enabled, matching the wizard. Percentages use the whole relevant catalogue for every model, including Lyrics. Unknown index counts remain null, empty catalogues have zero percent, and percentages are bounded to 0-100 without masking stale raw counts.

Shares the existing wizard count sources through tasks/model_coverage.py; the wizard's bands and lyrics-eligible denominator remain unchanged. Reuses source-scoped neural counting and adds cached paged-IVF directory/mapping counts. Local queries never substitute global coverage. The enablement/model-file-availability split remains intact.

The endpoints preserve the existing auth/setup policy, return sanitized errors and Cache-Control: no-store, and do not load encoders/search indexes, infer, analyze, or renew recording warmup. A cold local paged-IVF check reads compact directory IDs and source mappings, not cells/embeddings; scalar counts are cached for up to 30 seconds and invalidated on mapping/index replacement.

Includes API schemas and docs/model-coverage-api.md. No migration, dependency or Lumae frontend change.

Test

Local Windows x64 / Python 3.14.2 validation:

  • 164 passed, 1 skipped in model API, wizard, paged/neural index, availability, recording, header and import-architecture suites.
  • After adding generated-OpenAPI validation: 146 passed in model API, authentication, shared coverage and header suites (overlaps the preceding run).
  • Repository-wide Ruff, flake8, codespell and scoped mypy passed; generated OpenAPI includes both endpoints; tracked-file header checks and git diff --check passed.

Reproduce the relevant unit checks:

python -m pytest test/unit/test_model_coverage_api.py test/unit/test_model_coverage.py test/unit/test_setup_wizard_model_coverage.py test/unit/test_setup_wizard_model_switches.py test/unit/test_app_recording_search.py test/unit/test_neural_fingerprint.py test/unit/test_neural_fingerprint_index.py test/unit/test_paged_ivf.py test/unit/test_index_availability_cache.py test/unit/test_file_header_convention.py test/unit/test_import_architecture.py test/unit/test_app_auth.py -q

New real-PostgreSQL integration regression:

python -m pytest test/integration/test_model_coverage_api_integration.py -q

It verifies persisted directory/header counts, default legacy IDs, scoped canonical mappings, lyrics percentages and an emptied secondary source using an isolated schema in the disposable test database. It skips locally because no disposable PostgreSQL fixture is installed; review CI for the full unit/integration results. No live provider, ARM/NVIDIA or 150k-song deployment was tested locally.

Other useful information

Follows the maintainer's requested all-model API shape: #906 (comment)

Implementation and this description were prepared with Codex assistance.

Checklist

Type of change:

  • New feature
  • Documentation
  • Breaking change

Tested on media server:

  • Navidrome
  • Jellyfin
  • Emby
  • Lyrion

Updated:

  • Documentation
  • Unit test
  • Integration test

Other:

  • Checked performance on a big library (> 150k songs) works without issues

@rendyhd
rendyhd marked this pull request as ready for review September 12, 2026 18:10
@NeptuneHub

Copy link
Copy Markdown
Owner

Hi, thanks a lot for the work here! Before we go further I'd like to change the shape of this API, so let me explain what I have in mind.

What I need is one endpoint that any logged-in user can call (not admin only). For each model it should return:

  • enabled: on / off
  • global coverage: coverage over the whole catalogue, as a number and a percentage
  • local coverage: coverage over one specific server, only when a server is passed in the request, again as a number and a percentage

So it should cover all the models we show in the setup wizard (MusiCNN, DCLAP, Lyrics, Neural Fingerprint), not only the neural fingerprint one. At the moment the PR covers one model out of four, and nothing in the frontend calls the new route yet, so a normal user still doesn't see anything new.

Good news: most of the logic already exists. model_coverage_levels() in app_setup.py already computes coverage for all four models, and your get_scoped_status() already does the per-server counting. I think you can build the new endpoint mostly by reusing those two.

One more thing: please remove the version and the recording limits from this response. api_version, app_version and the whole recording block are a different topic, and mixing them here will make the API harder to keep stable.

If the client really needs the server version, let's not put it here. Let's create a GET /api/version in app.py, still gated from the fact that user need to be authenticated.

The rest is good and I'd like to keep it: the is_available() / model_files_available() split, the auth approach, and the tests. Please carry them over.

Thanks again!

@rendyhd rendyhd changed the title Expose read-only recording search capabilities Expose authenticated model coverage and application version APIs Sep 13, 2026
@rendyhd

rendyhd commented Sep 13, 2026

Copy link
Copy Markdown
Contributor Author

I've made the changes. Version is very useful when you want to integrate into an app. Now I can put a message up: In order to use you have to update to version

@rendyhd

rendyhd commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

after merging main tests now fail, i'll fix

@sonarqubecloud

Copy link
Copy Markdown

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants