feat(server/web/coverart): manual Re-search missing art button
POST /api/admin/cover-sources/research bumps cover_art_sources_meta. current_version unconditionally; the next enrichment pass re-eligibles every 'none' row. Existing positively-sourced rows are not affected — the version-mismatch eligibility rule only kicks in for 'none'. Admin Cover Art panel gains a "Re-search missing art" button that calls the endpoint and shows a confirmation toast. Operator's escape hatch when: - They've added a Last.fm key and want to retry failed rows immediately rather than waiting for the next scheduled scan. - An upstream provider's catalog has updated (e.g. Deezer added a back-catalog import). - They want to verify a fix end-to-end before the next scheduled scan fires. SettingsService.BumpVersion (the unconditional version of T5's BumpVersionIfProvidersChanged) is the single-call DB writer; both endpoints route through it. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,19 @@
|
||||
import { describe, it, expect, vi, beforeEach } from 'vitest';
|
||||
import { researchMissingArt } from './admin';
|
||||
|
||||
vi.mock('./client', () => ({
|
||||
api: { get: vi.fn(), post: vi.fn(), patch: vi.fn() }
|
||||
}));
|
||||
|
||||
import { api } from './client';
|
||||
|
||||
describe('admin research missing art API', () => {
|
||||
beforeEach(() => vi.clearAllMocks());
|
||||
|
||||
it('researchMissingArt POSTs the correct path and returns version', async () => {
|
||||
(api.post as unknown as ReturnType<typeof vi.fn>).mockResolvedValueOnce({ version: 7 });
|
||||
const got = await researchMissingArt();
|
||||
expect(api.post).toHaveBeenCalledWith('/api/admin/cover-sources/research', {});
|
||||
expect(got.version).toBe(7);
|
||||
});
|
||||
});
|
||||
@@ -320,6 +320,17 @@ export async function testCoverProvider(id: string): Promise<TestCoverProviderRe
|
||||
return api.post<TestCoverProviderResponse>(`/api/admin/cover-sources/${id}/test`, {});
|
||||
}
|
||||
|
||||
// Re-search missing art --------------------------------------------------
|
||||
|
||||
export type ResearchMissingArtResponse = { version: number };
|
||||
|
||||
// Bumps cover_art_sources_meta.current_version. Every 'none' row becomes
|
||||
// eligible for retry against the current provider chain on the next
|
||||
// enrichment pass. Existing positively-sourced rows are not affected.
|
||||
export async function researchMissingArt(): Promise<ResearchMissingArtResponse> {
|
||||
return api.post<ResearchMissingArtResponse>('/api/admin/cover-sources/research', {});
|
||||
}
|
||||
|
||||
// Settings rarely change in operator time. 60s staleTime; refetches
|
||||
// on window focus + after any mutation rather than polling.
|
||||
export function createCoverProvidersQuery() {
|
||||
|
||||
Reference in New Issue
Block a user