UNPKG

repomix

Version:

A tool to pack repository contents to single file for AI consumption

125 lines 4.76 kB
import gitUrlParse from 'git-url-parse'; import { RepomixError } from '../../shared/errorHandle.js'; import { logger } from '../../shared/logger.js'; // Check the short form of the GitHub URL. e.g. yamadashy/repomix const VALID_NAME_PATTERN = '[a-zA-Z0-9](?:[a-zA-Z0-9._-]*[a-zA-Z0-9])?'; const validShorthandRegex = new RegExp(`^${VALID_NAME_PATTERN}/${VALID_NAME_PATTERN}$`); export const isValidShorthand = (remoteValue) => { return validShorthandRegex.test(remoteValue); }; export const parseRemoteValue = (remoteValue, refs = []) => { if (isValidShorthand(remoteValue)) { logger.trace(`Formatting GitHub shorthand: ${remoteValue}`); return { repoUrl: `https://github.com/${remoteValue}.git`, remoteBranch: undefined, }; } try { const parsedFields = gitUrlParse(remoteValue, refs); // This will make parsedFields.toString() automatically append '.git' to the returned url parsedFields.git_suffix = true; const ownerSlashRepo = parsedFields.full_name.split('/').length > 1 ? parsedFields.full_name.split('/').slice(-2).join('/') : ''; if (ownerSlashRepo !== '' && !isValidShorthand(ownerSlashRepo)) { throw new RepomixError('Invalid owner/repo in repo URL'); } const repoUrl = parsedFields.toString(parsedFields.protocol); if (parsedFields.ref) { return { repoUrl: repoUrl, remoteBranch: parsedFields.ref, }; } if (parsedFields.commit) { return { repoUrl: repoUrl, remoteBranch: parsedFields.commit, }; } return { repoUrl: repoUrl, remoteBranch: undefined, }; } catch (error) { throw new RepomixError('Invalid remote repository URL or repository shorthand (owner/repo)'); } }; export const isValidRemoteValue = (remoteValue, refs = []) => { try { parseRemoteValue(remoteValue, refs); return true; } catch (error) { return false; } }; /** * Parses remote value and extracts GitHub repository information if it's a GitHub repo * Returns null if the remote value is not a GitHub repository */ export const parseGitHubRepoInfo = (remoteValue) => { try { // Handle shorthand format: owner/repo if (isValidShorthand(remoteValue)) { const [owner, repo] = remoteValue.split('/'); return { owner, repo }; } // For GitHub URLs with branch/tag/commit info, extract directly from URL try { const url = new URL(remoteValue); const allowedHosts = ['github.com', 'www.github.com']; if (allowedHosts.includes(url.hostname)) { const pathParts = url.pathname.split('/').filter(Boolean); if (pathParts.length >= 2) { const owner = pathParts[0]; const repo = pathParts[1].replace(/\.git$/, ''); const result = { owner, repo }; // Extract ref from URL patterns like /tree/branch or /commit/sha if (pathParts.length >= 4 && (pathParts[2] === 'tree' || pathParts[2] === 'commit')) { result.ref = pathParts.slice(3).join('/'); } return result; } } } catch (urlError) { // Fall back to git-url-parse if URL parsing fails logger.trace('URL parsing failed, falling back to git-url-parse:', urlError.message); } // Parse using git-url-parse for other cases const parsed = gitUrlParse(remoteValue); // Only proceed if it's a GitHub repository if (parsed.source !== 'github.com') { return null; } // Extract owner and repo from full_name (e.g., "owner/repo") const [owner, repo] = parsed.full_name.split('/'); if (!owner || !repo) { return null; } const result = { owner, repo: repo.replace(/\.git$/, ''), // Remove .git suffix }; // Add ref if available if (parsed.ref) { result.ref = parsed.ref; } else if (parsed.commit) { result.ref = parsed.commit; } return result; } catch (error) { logger.trace('Failed to parse GitHub repo info:', error.message); return null; } }; /** * Checks if a remote value represents a GitHub repository */ export const isGitHubRepository = (remoteValue) => { return parseGitHubRepoInfo(remoteValue) !== null; }; //# sourceMappingURL=gitRemoteParse.js.map