UNPKG

sourcesyncai-mcp

Version:

[![smithery badge](https://smithery.ai/badge/@pbteja1998/sourcesyncai-mcp)](https://smithery.ai/server/@pbteja1998/sourcesyncai-mcp)

415 lines (414 loc) 11.9 kB
import { WretchClient } from './wretch.js'; import { toLowerKebabCase } from './utils.js'; const SOURCESYNC_API_HOST_URL = 'https://api.sourcesync.ai'; /** * Log SourceSync API errors with detailed information */ export function logSourceSyncApiError(error, message) { console.error(`SourceSync API Error: ${message}`, { status: error.status, message: error.message, response: error.response, text: error.text, json: error.json, }); } /** * SourceSync API client for interacting with the SourceSync.ai API */ export class SourceSyncApiClient { static CHUNK_CONFIG = { chunkSize: 400, chunkOverlap: 50, }; namespaceId; client; /** * Create a new SourceSync API client */ constructor({ apiKey, tenantId, namespaceId, baseUrl = SOURCESYNC_API_HOST_URL, }) { this.namespaceId = namespaceId; this.client = WretchClient(baseUrl) .auth(`Bearer ${apiKey}`) .headers(tenantId ? { 'X-Tenant-ID': tenantId } : {}) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(400, (error) => { logSourceSyncApiError(error, 'Validation Error'); throw new Error('Validation Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(401, (error) => { logSourceSyncApiError(error, 'Authentication Error'); throw new Error('Authentication Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(403, (error) => { logSourceSyncApiError(error, 'Forbidden Error'); throw new Error('Forbidden Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(404, (error) => { logSourceSyncApiError(error, 'Not Found Error'); throw new Error('Not Found Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(405, (error) => { logSourceSyncApiError(error, 'Method Not Allowed Error'); throw new Error('Method Not Allowed Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(429, (error) => { logSourceSyncApiError(error, 'Too Many Requests Error'); throw new Error('Too Many Requests Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcher(500, (error) => { logSourceSyncApiError(error, 'Server Error'); throw new Error('Server Error'); }) // eslint-disable-next-line promise/prefer-await-to-callbacks .catcherFallback((error) => { logSourceSyncApiError(error, 'Server Error'); throw new Error('Server Error'); }); } /** * Get a namespace identifier from a brand ID */ static getNamespaceIdentifier({ brandId, }) { return `sitegpt_${brandId}`; } /** * Create a new namespace */ async createNamespace({ name, fileStorageConfig, vectorStorageConfig, embeddingModelConfig, webScraperConfig, }) { return this.client .url('/v1/namespaces') .json({ name, fileStorageConfig, vectorStorageConfig, embeddingModelConfig, webScraperConfig, }) .post() .json(); } /** * List all namespaces */ async listNamespaces() { return this.client .url('/v1/namespaces') .get() .json(); } /** * Get a namespace by ID */ async getNamespace() { return this.client .url(`/v1/namespaces/${this.namespaceId}`) .get() .json(); } /** * Update a namespace */ async updateNamespace({ fileStorageConfig, vectorStorageConfig, embeddingModelConfig, webScraperConfig, notionConfig, googleDriveConfig, dropboxConfig, onedriveConfig, boxConfig, sharepointConfig, }) { return this.client .url(`/v1/namespaces/${this.namespaceId}`) .json({ fileStorageConfig, vectorStorageConfig, embeddingModelConfig, webScraperConfig, notionConfig, googleDriveConfig, dropboxConfig, onedriveConfig, boxConfig, sharepointConfig, }) .patch() .json(); } /** * Delete a namespace */ async deleteNamespace() { return this.client .url(`/v1/namespaces/${this.namespaceId}`) .delete() .json(); } /** * Create a new connection */ async createConnection({ name, connector, clientRedirectUrl, }) { return this.client .url('/v1/connections') .json({ namespaceId: this.namespaceId, name, connector, clientRedirectUrl, }) .post() .json(); } /** * List all connections */ async listConnections({ connector, }) { return this.client .url('/v1/connections') .query({ namespaceId: this.namespaceId, connector }) .get() .json(); } /** * Get a connection by ID */ async getConnection({ connectionId, }) { return this.client .url(`/v1/connections/${connectionId}`) .query({ namespaceId: this.namespaceId }) .get() .json(); } /** * Update a connection */ async updateConnection({ connectionId, name, clientRedirectUrl, }) { return this.client .url(`/v1/connections/${connectionId}`) .json({ namespaceId: this.namespaceId, name, clientRedirectUrl, }) .patch() .json(); } /** * Revoke a connection */ async revokeConnection({ connectionId, }) { return this.client .url(`/v1/connections/${connectionId}/revoke`) .json({ namespaceId: this.namespaceId, }) .post() .json(); } /** * Ingest text content */ async ingestText({ ingestConfig, }) { return this.client .url('/v1/ingest/text') .json({ namespaceId: this.namespaceId, ingestConfig: { ...ingestConfig, chunkConfig: SourceSyncApiClient.CHUNK_CONFIG, }, }) .post() .json(); } /** * Ingest a file */ async ingestFile({ file, metadata, }) { return this.client .url('/v1/ingest/file') .formData({ namespaceId: this.namespaceId, file, metadata: JSON.stringify(metadata), chunkConfig: JSON.stringify(SourceSyncApiClient.CHUNK_CONFIG), }) .post() .json(); } /** * Ingest URLs */ async ingestUrls({ ingestConfig, }) { return this.client .url('/v1/ingest/urls') .json({ namespaceId: this.namespaceId, ingestConfig: { ...ingestConfig, chunkConfig: SourceSyncApiClient.CHUNK_CONFIG, }, }) .post() .json(); } /** * Ingest a sitemap */ async ingestSitemap({ ingestConfig, }) { return this.client .url('/v1/ingest/sitemap') .json({ namespaceId: this.namespaceId, ingestConfig: { ...ingestConfig, chunkConfig: SourceSyncApiClient.CHUNK_CONFIG, }, }) .post() .json(); } /** * Ingest a website */ async ingestWebsite({ ingestConfig, }) { return this.client .url('/v1/ingest/website') .json({ namespaceId: this.namespaceId, ingestConfig: { ...ingestConfig, chunkConfig: SourceSyncApiClient.CHUNK_CONFIG, }, }) .post() .json(); } /** * Ingest content from a connector */ async ingestConnector({ ingestConfig, }) { return this.client .url(`/v1/ingest/${toLowerKebabCase(ingestConfig.source)}`) .json({ namespaceId: this.namespaceId, ingestConfig: { ...ingestConfig, chunkConfig: SourceSyncApiClient.CHUNK_CONFIG, }, }) .post() .json(); } /** * Get the status of an ingest job run */ async getIngestJobRunStatus({ ingestJobRunId, }) { return this.client .url(`/v1/ingest-job-runs/${ingestJobRunId}`) .query({ namespaceId: this.namespaceId }) .get() .json(); } /** * Get documents */ async getDocuments({ filterConfig, includeConfig, pagination, }) { const response = await this.client .url(`/v1/documents`) .json({ namespaceId: this.namespaceId, filterConfig, includeConfig, pagination, }) .post() .json(); return { data: response.data.documents, hasNextPage: response.data.hasNextPage, nextCursor: response.data.nextCursor, statsBySource: response.data.statsBySource, statsByStatus: response.data.statsByStatus, }; } /** * Update documents */ async updateDocuments({ filterConfig, data, }) { return this.client .url(`/v1/documents`) .json({ namespaceId: this.namespaceId, filterConfig, data, }) .patch() .json(); } /** * Delete documents */ async deleteDocuments({ filterConfig, }) { return this.client .url(`/v1/documents`) .json({ namespaceId: this.namespaceId, filterConfig, }) .delete() .json(); } /** * Resync documents */ async resyncDocuments({ filterConfig, }) { return this.client .url(`/v1/documents/resync`) .json({ namespaceId: this.namespaceId, filterConfig, }) .post() .json(); } /** * Perform a semantic search */ async semanticSearch({ query, topK, scoreThreshold, filter, searchType, }) { return this.client .url('/v1/search') .json({ query, namespaceId: this.namespaceId, topK, scoreThreshold, filter, searchType, }) .post() .json(); } /** * Perform a hybrid search */ async hybridSearch({ query, topK, scoreThreshold, filter, hybridConfig, searchType, }) { return this.client .url('/v1/search/hybrid') .json({ query, namespaceId: this.namespaceId, topK, scoreThreshold, filter, hybridConfig, searchType, }) .post() .json(); } } /** * Create a new SourceSync API client */ export function sourcesync({ apiKey, tenantId, namespaceId, }) { return new SourceSyncApiClient({ apiKey, tenantId, namespaceId }); }