Skip to main content
Glama

Kagi MCP

by yuki-yano
kagi-client.ts3.66 kB
import axios, { AxiosInstance } from 'axios'; export interface SearchResult { t: number; title: string; url: string; snippet: string; published?: string; } export interface SearchResponse { data: SearchResult[]; } export interface SummarizerOptions { url: string; engine?: 'cecil' | 'agnes' | 'daphne' | 'muriel'; summary_type?: 'summary' | 'takeaway'; target_language?: string; } export interface SummarizerResponse { data: { output: string; }; } export class KagiClient { private axios: AxiosInstance; private apiKey: string; constructor() { const apiKey = process.env.KAGI_API_KEY; if (!apiKey) { throw new Error('KAGI_API_KEY environment variable is required'); } this.apiKey = apiKey; this.axios = axios.create({ baseURL: 'https://kagi.com/api/v0', headers: { 'Authorization': `Bot ${this.apiKey}`, 'Content-Type': 'application/json', }, timeout: 30000, }); } async search(query: string): Promise<SearchResponse> { try { const response = await this.axios.get('/search', { params: { q: query }, }); return response.data; } catch (error) { if (axios.isAxiosError(error)) { let errorMessage = 'Unknown error'; if (error.response?.data) { if (typeof error.response.data === 'string') { errorMessage = error.response.data; } else if (error.response.data.error) { // Kagi API returns error as an array if (Array.isArray(error.response.data.error)) { errorMessage = error.response.data.error.map((e: any) => e.msg).join('; '); } else { errorMessage = error.response.data.error; } } else if (error.response.data.message) { errorMessage = error.response.data.message; } else { errorMessage = JSON.stringify(error.response.data); } } else { errorMessage = error.response?.statusText || error.message; } const statusCode = error.response?.status; throw new Error(`Kagi search error (${statusCode}): ${errorMessage}`); } throw error; } } async summarize(options: SummarizerOptions): Promise<SummarizerResponse> { try { const response = await this.axios.post('/summarize', { url: options.url, engine: options.engine || 'cecil', summary_type: options.summary_type, target_language: options.target_language, }); return response.data; } catch (error) { if (axios.isAxiosError(error)) { let errorMessage = 'Unknown error'; if (error.response?.data) { if (typeof error.response.data === 'string') { errorMessage = error.response.data; } else if (error.response.data.error) { // Kagi API returns error as an array if (Array.isArray(error.response.data.error)) { errorMessage = error.response.data.error.map((e: any) => e.msg).join('; '); } else { errorMessage = error.response.data.error; } } else if (error.response.data.message) { errorMessage = error.response.data.message; } else { errorMessage = JSON.stringify(error.response.data); } } else { errorMessage = error.response?.statusText || error.message; } const statusCode = error.response?.status; throw new Error(`Kagi summarizer error (${statusCode}): ${errorMessage}`); } throw error; } } }

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/yuki-yano/kagi-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server