Files
openmaic/OpenMAIC/tests/web-search/searxng.test.ts
2026-08-16 14:58:47 +08:00

81 lines
2.5 KiB
TypeScript

import { beforeEach, describe, expect, it, vi } from 'vitest';
const proxyFetchMock = vi.hoisted(() => vi.fn());
vi.mock('@/lib/server/proxy-fetch', () => ({
proxyFetch: proxyFetchMock,
}));
import { buildSearxngSearchUrl, searchWithSearxng } from '@/lib/web-search/searxng';
describe('buildSearxngSearchUrl', () => {
it('builds JSON search URLs from instance root or /search base paths', () => {
expect(buildSearxngSearchUrl('http://192.168.161.100:6060', 'hello')).toBe(
'http://192.168.161.100:6060/search?q=hello&format=json',
);
expect(buildSearxngSearchUrl('http://192.168.161.100:6060/search', 'hello')).toBe(
'http://192.168.161.100:6060/search?q=hello&format=json',
);
});
});
describe('searchWithSearxng', () => {
beforeEach(() => {
proxyFetchMock.mockReset();
});
it('requires a configured base URL', async () => {
await expect(searchWithSearxng({ query: 'test' })).rejects.toThrow(
'SearXNG base URL is not configured',
);
});
it('calls SearXNG JSON API and maps organic results', async () => {
proxyFetchMock.mockResolvedValueOnce(
new Response(
JSON.stringify({
query: 'test query',
results: [
{
title: 'First result',
url: 'https://example.com/a',
content: 'Snippet A',
score: 3.1,
},
{ title: 'Second result', url: 'https://example.com/b', content: 'Snippet B' },
],
}),
{ status: 200, headers: { 'content-type': 'application/json' } },
),
);
const result = await searchWithSearxng({
query: 'test query',
baseUrl: 'http://192.168.161.100:6060',
maxResults: 2,
});
const requestedUrl = new URL(proxyFetchMock.mock.calls[0][0] as string);
expect(requestedUrl.origin).toBe('http://192.168.161.100:6060');
expect(requestedUrl.pathname).toBe('/search');
expect(requestedUrl.searchParams.get('q')).toBe('test query');
expect(requestedUrl.searchParams.get('format')).toBe('json');
expect(proxyFetchMock.mock.calls[0][1]).toMatchObject({ method: 'GET' });
expect(result.sources).toEqual([
{
title: 'First result',
url: 'https://example.com/a',
content: 'Snippet A',
score: 3.1,
},
{
title: 'Second result',
url: 'https://example.com/b',
content: 'Snippet B',
score: 0.95,
},
]);
expect(result.query).toBe('test query');
});
});