🚫 feat: Add Support for none Reranker Type in Web Search Config (#12765)

Most of the codebase already supports the concept of *not* using a reranker w/
web search, except there was no way to initially setup an absent reranker
component.

Now there's a special path for skipping the reranker auth when loading web
search config, which allows for skipping the reranker when using web search.
This commit is contained in:
Daniel Lew 2026-04-28 19:17:04 -05:00 committed by GitHub
parent 84043432a5
commit 2503365c44
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
5 changed files with 51 additions and 1 deletions

View file

@ -818,6 +818,46 @@ describe('web.ts', () => {
expect(cohereCalls.length).toBe(0);
});
it('should handle a rerankerType of `none`', async () => {
// Initialize a webSearchConfig with a specific rerankerType
const webSearchConfig: TCustomConfig['webSearch'] = {
serperApiKey: '${SERPER_API_KEY}',
searxngInstanceUrl: '${SEARXNG_INSTANCE_URL}',
searxngApiKey: '${SEARXNG_API_KEY}',
firecrawlApiKey: '${FIRECRAWL_API_KEY}',
firecrawlApiUrl: '${FIRECRAWL_API_URL}',
safeSearch: SafeSearchTypes.MODERATE,
rerankerType: 'none' as RerankerTypes,
};
// Mock successful authentication
mockLoadAuthValues.mockImplementation(({ authFields }) => {
const result: Record<string, string> = {};
authFields.forEach((field: string) => {
result[field] =
field === 'FIRECRAWL_API_URL' ? 'https://api.firecrawl.dev' : 'test-api-key';
});
return Promise.resolve(result);
});
const result = await loadWebSearchAuth({
userId,
webSearchConfig,
loadAuthValues: mockLoadAuthValues,
});
expect(result.authenticated).toBe(true);
expect(result.authResult.rerankerType).toBe('none');
// Verify that we didn't request any reranker keys
const cohereCalls = mockLoadAuthValues.mock.calls.filter(
(call) =>
call[0].authFields.includes('COHERE_API_KEY') ||
call[0].authFields.includes('JINA_API_KEY'),
);
expect(cohereCalls.length).toBe(0);
});
it('should handle invalid specified service gracefully', async () => {
// Initialize a webSearchConfig with an invalid searchProvider
const webSearchConfig: TCustomConfig['webSearch'] = {

View file

@ -123,6 +123,12 @@ export async function loadWebSearchAuth({
specificService = webSearchConfig.scraperProvider as unknown as ServiceType;
} else if (category === SearchCategories.RERANKERS && webSearchConfig?.rerankerType) {
specificService = webSearchConfig.rerankerType as unknown as ServiceType;
// Special case: skipping the reranker means skipping auth as well
if (specificService === 'none') {
authResult.rerankerType = specificService as RerankerTypes;
return [true, false];
}
}
// If a specific service is specified, only check that one

View file

@ -937,6 +937,7 @@ export enum ScraperProviders {
export enum RerankerTypes {
JINA = 'jina',
COHERE = 'cohere',
NONE = 'none',
}
export enum SafeSearchTypes {

View file

@ -56,6 +56,7 @@ describe('loadWebSearchConfig', () => {
jinaApiUrl: '${JINA_API_URL}',
cohereApiKey: '${COHERE_API_KEY}',
safeSearch: SafeSearchTypes.MODERATE,
rerankerType: undefined,
});
});

View file

@ -1,4 +1,4 @@
import { SafeSearchTypes } from 'librechat-data-provider';
import { RerankerTypes, SafeSearchTypes } from 'librechat-data-provider';
import type { TCustomConfig } from 'librechat-data-provider';
import type { TWebSearchKeys, TWebSearchCategories } from '~/types/web';
@ -73,6 +73,7 @@ export function loadWebSearchConfig(
const jinaApiUrl = config?.jinaApiUrl ?? '${JINA_API_URL}';
const cohereApiKey = config?.cohereApiKey ?? '${COHERE_API_KEY}';
const safeSearch = config?.safeSearch ?? SafeSearchTypes.MODERATE;
const rerankerType = config?.rerankerType;
return {
...config,
@ -86,5 +87,6 @@ export function loadWebSearchConfig(
firecrawlApiUrl,
firecrawlVersion,
searxngInstanceUrl,
rerankerType,
};
}