UNPKG

sourcesailor

Version:

A CLI tool for analyzing and documenting codebases

107 lines (106 loc) 4.12 kB
import fs from 'fs'; import os from 'os'; import path from 'path'; export function readConfig() { const homeDir = os.homedir(); const configFile = path.join(homeDir, '.SourceSailor', 'config.json'); if (fs.existsSync(configFile)) { try { const config = JSON.parse(fs.readFileSync(configFile, 'utf8')); return config; } catch (error) { console.error('Error parsing config file:', error); } return {}; } return {}; } export function writeConfig(config) { const homeDir = os.homedir(); const configDir = path.join(homeDir, '.SourceSailor'); const configFile = path.join(configDir, 'config.json'); if (!fs.existsSync(configDir)) { fs.mkdirSync(configDir, { recursive: true }); } fs.writeFileSync(configFile, JSON.stringify(config, null, 2)); } export function addAnalysisInGitIgnore(projectRoot) { // First check if the project root has gitignore file, if the file is not found don't create one. // If the file is found, append .SourceSailor/analysis to the file. const gitignoreFile = path.join(projectRoot, '.gitignore'); if (fs.existsSync(gitignoreFile)) { const gitignoreContent = fs.readFileSync(gitignoreFile, 'utf8'); if (!gitignoreContent.includes('.SourceSailor/analysis')) { fs.appendFileSync(gitignoreFile, '\n.SourceSailor/analysis'); } } } export function writeAnalysis(projectRoot, analysisName, analysisContent, isJson = false, isProjectRoot = false) { const analysisDir = isProjectRoot ? path.join(projectRoot, '.SourceSailor', 'analysis') : path.join(projectRoot, 'analysis'); if (!fs.existsSync(analysisDir)) { fs.mkdirSync(analysisDir, { recursive: true }); } if (isJson) { const analysisFile = path.join(analysisDir, `${analysisName}.json`); fs.writeFileSync(analysisFile, JSON.stringify(analysisContent, null, 4)); } else { const analysisFile = path.join(analysisDir, `${analysisName}.md`); fs.writeFileSync(analysisFile, analysisContent); } } export function writeError(projectRoot, errorType, errorContent, errorMssage) { const errorDir = path.join(projectRoot, 'errors'); if (!fs.existsSync(errorDir)) { fs.mkdirSync(errorDir, { recursive: true }); } const errorFile = path.join(errorDir, `${errorType}.txt`); fs.writeFileSync(errorFile, `${errorContent}\n\n${errorMssage}`); } export function getAnalysis(projectRoot, isProjectRoot) { const analysis = {}; const analysisDir = isProjectRoot ? path.join(projectRoot, '.SourceSailor', 'analysis') : path.join(projectRoot, 'analysis'); if (!fs.existsSync(analysisDir)) { return analysis; } const entries = fs.readdirSync(analysisDir); for (const entry of entries) { const fullPath = path.join(analysisDir, entry); const isDirectory = fs.statSync(fullPath).isDirectory(); // console.log({entry}) const fileName = path.basename(entry, path.extname(entry)); if (isDirectory) { analysis[fileName] = getAnalysis(fullPath, false); } else { analysis[fileName] = fs.readFileSync(fullPath, 'utf-8'); } } return analysis; } export async function processStream(iterator, processChunk) { let fullResponse = ''; const { value, done } = await iterator.next(); while (done) { const message = processChunk(value); process.stdout.write(message); fullResponse += message; } return fullResponse; } export function maskSensitiveInfo(input) { // This is a simple implementation. You might want to enhance it based on your specific needs. const sensitivePatterns = [ /api[-_]?key/i, /password/i, /secret/i, /token/i, /credential/i ]; let maskedInput = input; for (const pattern of sensitivePatterns) { maskedInput = maskedInput.replace(new RegExp(`(${pattern.source}\\s*[=:])\\s*["']?[^"'\\s]+["']?`, 'gi'), '$1 "********"'); } return maskedInput; }