95 lines
4.2 KiB
TypeScript
95 lines
4.2 KiB
TypeScript
import { describe, expect, it, vi } from 'vitest';
|
|
import { WatermarksService } from '../src/watermarks/watermarks.service.js';
|
|
|
|
const templateId = '46ea1f9c-28d0-4b32-92e1-3d4e74ad7757';
|
|
|
|
const templateRow = (isDefault: boolean) => ({
|
|
id: templateId,
|
|
name: '品牌水印',
|
|
kind: 'text' as const,
|
|
is_default: isDefault,
|
|
current_version: 1,
|
|
created_at: new Date('2026-09-25T00:00:00Z'),
|
|
updated_at: new Date('2026-09-25T00:00:00Z'),
|
|
revision: 1,
|
|
text_content: 'Atlas',
|
|
image_asset_id: null,
|
|
font_code: 'NotoSans',
|
|
font_size_px: 15,
|
|
opacity: '0.2600',
|
|
scale_ratio: null,
|
|
image_size_px: null,
|
|
border_radius_px: 0,
|
|
position: 'center',
|
|
position_x: '0.5000',
|
|
position_y: '0.5000',
|
|
});
|
|
|
|
describe('工作空间默认水印', () => {
|
|
it('切换默认后返回新状态,重复设置不会再写入', async () => {
|
|
let isDefault = false;
|
|
const statements: string[] = [];
|
|
const query = vi.fn(async (sql: string) => {
|
|
statements.push(sql);
|
|
if (sql.includes('SELECT id FROM atlas.workspaces')) return { rows: [{ id: 'workspace' }] };
|
|
if (sql.includes('SELECT template.id')) return { rows: [templateRow(isDefault)] };
|
|
if (sql.includes('SET is_default = false')) return { rows: [] };
|
|
if (sql.includes('SET is_default = true')) {
|
|
isDefault = true;
|
|
return { rows: [] };
|
|
}
|
|
throw new Error(`未知 SQL: ${sql}`);
|
|
});
|
|
const run = vi.fn(async (_input: unknown, work: (tx: { query: typeof query }) => Promise<unknown>) =>
|
|
work({ query }));
|
|
const service = new WatermarksService(
|
|
{ run } as unknown as ConstructorParameters<typeof WatermarksService>[0],
|
|
{} as ConstructorParameters<typeof WatermarksService>[1],
|
|
);
|
|
|
|
const first = await service.setDefault('workspace', 'user', templateId, 'key-1');
|
|
expect(first).toMatchObject({ status: 200, body: { data: { id: templateId, is_default: true } } });
|
|
expect(statements.filter((sql) => sql.includes('SET is_default'))).toHaveLength(2);
|
|
expect(statements[0]).toContain('FOR UPDATE');
|
|
|
|
const second = await service.setDefault('workspace', 'user', templateId, 'key-2');
|
|
expect(second).toMatchObject({ status: 200, body: { data: { is_default: true } } });
|
|
expect(statements.filter((sql) => sql.includes('SET is_default'))).toHaveLength(2);
|
|
expect(run).toHaveBeenCalledWith(expect.objectContaining({
|
|
method: 'PUT',
|
|
path: `/api/watermark-templates/${templateId}/default`,
|
|
}), expect.any(Function));
|
|
});
|
|
|
|
it('未设置默认时返回 null', async () => {
|
|
const query = vi.fn(async () => ({ rows: [] }));
|
|
const workspaceTransaction = vi.fn(async (_workspaceId: string, work: (tx: { query: typeof query }) => Promise<unknown>) =>
|
|
work({ query }));
|
|
const service = new WatermarksService(
|
|
{} as ConstructorParameters<typeof WatermarksService>[0],
|
|
{ workspaceTransaction } as unknown as ConstructorParameters<typeof WatermarksService>[1],
|
|
);
|
|
|
|
expect(await service.getDefault('workspace')).toBeNull();
|
|
expect(query.mock.calls).toHaveLength(1);
|
|
expect(workspaceTransaction).toHaveBeenCalledWith('workspace', expect.any(Function));
|
|
});
|
|
|
|
it('删除默认模板时同时清除默认标记', async () => {
|
|
const query = vi.fn(async (sql: string) => {
|
|
if (sql.includes('SELECT template.id')) return { rows: [templateRow(true)] };
|
|
return { rows: [] };
|
|
});
|
|
const run = vi.fn(async (_input: unknown, work: (tx: { query: typeof query }) => Promise<unknown>) =>
|
|
work({ query }));
|
|
const service = new WatermarksService(
|
|
{ run } as unknown as ConstructorParameters<typeof WatermarksService>[0],
|
|
{} as ConstructorParameters<typeof WatermarksService>[1],
|
|
);
|
|
|
|
expect(await service.remove('workspace', 'user', templateId, 'key')).toEqual({ status: 204, body: null });
|
|
expect(query.mock.calls.some(([sql]) => sql.includes("status = 'archived'")
|
|
&& sql.includes('is_default = false'))).toBe(true);
|
|
});
|
|
});
|