import { describe, expect, it } from 'vitest'; import type { Photo } from './types'; import { computeViewerSource, editPendingOf } from './viewer-source'; const BASE = { originalUrl: '/orig.jpg', previewUrl: '/preview.jpg', editUrl: '/edit.jpg', editPreviewUrl: '/edit-preview.jpg' }; describe('computeViewerSource', () => { it('shows the server render when it matches the saved edits', () => { const src = computeViewerSource({ zoomed: false, dirty: false, editPending: false, localParamsEmpty: false, ...BASE }); expect(src.useBase).toBe(false); expect(src.serverSrc).toBe('/edit-preview.jpg'); expect(src.baseSrc).toBe('/preview.jpg'); }); it('uses the full-size variants in zoom', () => { const src = computeViewerSource({ zoomed: true, dirty: false, editPending: false, localParamsEmpty: false, ...BASE }); expect(src.serverSrc).toBe('/edit.jpg'); expect(src.baseSrc).toBe('/orig.jpg'); }); it('keeps the client preview while local edits are unsaved', () => { const src = computeViewerSource({ zoomed: true, dirty: true, editPending: false, localParamsEmpty: false, ...BASE }); expect(src.useBase).toBe(true); expect(src.drawCanvas).toBe(true); expect(src.baseSrc).toBe('/orig.jpg'); }); it('shows the base version immediately when the edits are reset to defaults', () => { const src = computeViewerSource({ zoomed: true, dirty: true, editPending: false, localParamsEmpty: true, ...BASE }); expect(src.useBase).toBe(true); expect(src.drawCanvas).toBe(false); expect(src.baseSrc).toBe('/orig.jpg'); }); it('ignores a stale server render while the saved edits are still rendering', () => { const src = computeViewerSource({ zoomed: false, dirty: false, editPending: true, localParamsEmpty: false, ...BASE }); expect(src.useBase).toBe(true); expect(src.drawCanvas).toBe(true); }); it('keeps the client preview when a second edit is pending over an old render', () => { const src = computeViewerSource({ zoomed: true, dirty: false, editPending: true, localParamsEmpty: false, ...BASE }); expect(src.useBase).toBe(true); expect(src.drawCanvas).toBe(true); expect(src.baseSrc).toBe('/orig.jpg'); }); it('falls back to the base version when there is no edit render', () => { const src = computeViewerSource({ zoomed: false, dirty: false, editPending: false, localParamsEmpty: true, originalUrl: '/orig.jpg', previewUrl: '/preview.jpg' }); expect(src.useBase).toBe(true); expect(src.drawCanvas).toBe(false); expect(src.serverSrc).toBe('/preview.jpg'); }); it('prefers the full-size base when zoomed without a preview', () => { const src = computeViewerSource({ zoomed: true, dirty: false, editPending: false, localParamsEmpty: true, originalUrl: '/orig.jpg' }); expect(src.baseSrc).toBe('/orig.jpg'); expect(src.serverSrc).toBe('/orig.jpg'); }); it('treats the old backend without edit_pending as a finished render', () => { expect(editPendingOf(undefined)).toBe(false); expect(editPendingOf({ id: 'p' } as Photo)).toBe(false); expect(editPendingOf({ id: 'p', edit_pending: true } as Photo)).toBe(true); }); });