Skip to main content
Glama
MIT License
27,120
19,780
  • Linux
  • Apple
languageParser.ts•3.24 kB
import * as path from 'node:path'; import { Parser, Query } from 'web-tree-sitter'; import { RepomixError } from '../../shared/errorHandle.js'; import { logger } from '../../shared/logger.js'; import { ext2Lang } from './ext2Lang.js'; import { lang2Query, type SupportedLang } from './lang2Query.js'; import { loadLanguage } from './loadLanguage.js'; import { createParseStrategy, type ParseStrategy } from './parseStrategies/ParseStrategy.js'; interface LanguageResources { lang: SupportedLang; parser: Parser; query: Query; strategy: ParseStrategy; } export class LanguageParser { private loadedResources: Map<SupportedLang, LanguageResources> = new Map(); private initialized = false; private getFileExtension(filePath: string): string { return path.extname(filePath).toLowerCase().slice(1); } private async prepareLang(name: SupportedLang): Promise<LanguageResources> { try { const lang = await loadLanguage(name); const parser = new Parser(); parser.setLanguage(lang); const query = new Query(lang, lang2Query[name]); const strategy = createParseStrategy(name); const resources: LanguageResources = { lang: name, parser, query, strategy, }; this.loadedResources.set(name, resources); return resources; } catch (error) { const message = error instanceof Error ? error.message : String(error); throw new RepomixError(`Failed to prepare language ${name}: ${message}`); } } private async getResources(name: SupportedLang): Promise<LanguageResources> { if (!this.initialized) { throw new RepomixError('LanguageParser is not initialized. Call init() first.'); } const resources = this.loadedResources.get(name); if (!resources) { return this.prepareLang(name); } return resources; } public async getParserForLang(name: SupportedLang): Promise<Parser> { const resources = await this.getResources(name); return resources.parser; } public async getQueryForLang(name: SupportedLang): Promise<Query> { const resources = await this.getResources(name); return resources.query; } public async getStrategyForLang(name: SupportedLang): Promise<ParseStrategy> { const resources = await this.getResources(name); return resources.strategy; } public guessTheLang(filePath: string): SupportedLang | undefined { const ext = this.getFileExtension(filePath); if (!Object.keys(ext2Lang).includes(ext)) { return undefined; } return ext2Lang[ext as keyof typeof ext2Lang] as SupportedLang; } public async init(): Promise<void> { if (this.initialized) { return; } try { await Parser.init(); this.initialized = true; } catch (error) { const message = error instanceof Error ? error.message : String(error); throw new RepomixError(`Failed to initialize parser: ${message}`); } } public async dispose(): Promise<void> { for (const resources of this.loadedResources.values()) { resources.parser.delete(); logger.debug(`Deleted parser for language: ${resources.lang}`); } this.loadedResources.clear(); this.initialized = false; } }

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/yamadashy/repomix'

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