Skip to main content
Glama
cross-resource-validator.ts4.25 kB
import { UniversalResourceType } from '../types.js'; import { ErrorType, HttpStatusCode, UniversalValidationError, } from '../errors/validation-errors.js'; import { getLazyAttioClient } from '../../../../api/lazy-client.js'; export class CrossResourceValidator { static async validateCompanyExists(companyId: string): Promise<{ exists: boolean; error?: { type: 'not_found' | 'api_error' | 'invalid_format'; message: string; httpStatusCode: HttpStatusCode; }; }> { if ( !companyId || typeof companyId !== 'string' || companyId.trim().length === 0 ) { return { exists: false, error: { type: 'invalid_format', message: 'Company ID must be a non-empty string', httpStatusCode: HttpStatusCode.UNPROCESSABLE_ENTITY, }, }; } try { const client = getLazyAttioClient(); await client.get(`/objects/companies/records/${companyId.trim()}`); return { exists: true }; } catch (error: unknown) { const responseStatus = typeof error === 'object' && error !== null && 'response' in error && typeof (error as { response?: { status?: number } }).response === 'object' ? (error as { response?: { status?: number } }).response?.status : undefined; if (responseStatus === 404) { return { exists: false, error: { type: 'not_found', message: `Company with ID '${companyId}' does not exist`, httpStatusCode: HttpStatusCode.NOT_FOUND, }, }; } return { exists: false, error: { type: 'api_error', message: `Failed to validate company existence: ${ typeof error === 'object' && error !== null && 'message' in error ? String((error as { message?: unknown }).message) : 'Unknown API error' }`, httpStatusCode: HttpStatusCode.BAD_GATEWAY, }, }; } } static async validateRecordRelationships( resourceType: UniversalResourceType, recordData: Record<string, unknown> | null | undefined ): Promise<void> { if (!recordData || typeof recordData !== 'object') return; switch (resourceType) { case UniversalResourceType.PEOPLE: { const recordDataObj = recordData as Record<string, unknown>; const companyField = recordDataObj.company as | Record<string, unknown> | string | undefined; const nestedCompanyId = typeof companyField === 'object' && companyField !== null && 'id' in companyField ? (companyField as Record<string, unknown>).id : undefined; const companyId = recordDataObj.company_id ?? nestedCompanyId ?? companyField; if (companyId) { const companyIdString = String(companyId); const validationResult = await this.validateCompanyExists(companyIdString); if (!validationResult.exists) { const error = validationResult.error!; throw new UniversalValidationError( error.message, error.type === 'api_error' ? ErrorType.API_ERROR : ErrorType.USER_ERROR, { field: 'company_id', suggestion: error.type === 'not_found' ? 'Verify the company ID exists, or create the company first' : 'Check your API connection and try again', example: error.type === 'not_found' ? `Try searching for companies first: search-records with resource_type: 'companies'` : undefined, httpStatusCode: error.httpStatusCode, } ); } } break; } case UniversalResourceType.RECORDS: // Placeholder for custom record relations validation break; case UniversalResourceType.TASKS: // Placeholder: validate referenced record existence if needed break; default: break; } } }

Latest Blog Posts

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/kesslerio/attio-mcp-server'

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