@codervisor/devlog-ai
Version:
AI Chat History Extractor & Docker-based Automation - TypeScript implementation for GitHub Copilot and other AI coding assistants with automated testing capabilities
149 lines (148 loc) • 6.28 kB
JavaScript
/**
* Chat import service for importing chat history from various sources
*
* This service handles importing chat data through ChatHub (GitHub Copilot, etc.)
* into the devlog storage system with proper workspace mapping and linking.
*/
export class ChatHubService {
storageProvider;
activeImports = new Map();
constructor(storageProvider) {
this.storageProvider = storageProvider;
}
async ingestChatSessions(sessions) {
const importId = this.generateImportId();
const progress = {
importId,
status: 'running',
source: sessions[0]?.agent === 'GitHub Copilot' ? 'github-copilot' : 'manual',
progress: {
totalSessions: sessions.length,
processedSessions: 0,
totalMessages: 0,
processedMessages: 0,
percentage: 0,
},
startedAt: new Date().toISOString(),
};
this.activeImports.set(importId, progress);
try {
console.log(`[ChatHub] Ingesting ${sessions.length} chat sessions`);
for (const session of sessions) {
await this.storageProvider.saveChatSession(session);
progress.progress.processedSessions++;
progress.progress.percentage = Math.round((progress.progress.processedSessions / progress.progress.totalSessions) * 100);
}
progress.status = 'completed';
progress.completedAt = new Date().toISOString();
progress.results = {
importedSessions: sessions.length,
importedMessages: 0,
linkedSessions: 0,
errors: 0,
warnings: [],
};
console.log(`[ChatHub] Successfully ingested ${sessions.length} sessions`);
return progress;
}
catch (error) {
console.error('[ChatHub] Error ingesting sessions:', error);
progress.status = 'failed';
progress.completedAt = new Date().toISOString();
progress.error = {
message: error instanceof Error ? error.message : 'Unknown error',
details: { stack: error instanceof Error ? error.stack : undefined },
};
throw error;
}
}
async ingestChatMessages(messages) {
try {
console.log(`[ChatHub] Ingesting ${messages.length} chat messages`);
await this.storageProvider.saveChatMessages(messages);
console.log(`[ChatHub] Successfully ingested ${messages.length} messages`);
}
catch (error) {
console.error('[ChatHub] Error ingesting messages:', error);
throw error;
}
}
async processBulkChatData(data) {
const importId = this.generateImportId();
const progress = {
importId,
status: 'running',
source: data.source,
progress: {
totalSessions: data.sessions.length,
processedSessions: 0,
totalMessages: data.messages.length,
processedMessages: 0,
percentage: 0,
},
startedAt: new Date().toISOString(),
};
this.activeImports.set(importId, progress);
try {
console.log(`[ChatHub] Processing bulk data: ${data.sessions.length} sessions, ${data.messages.length} messages from ${data.source}`);
// Process workspace info if provided
if (data.workspaceInfo) {
await this.storageProvider.saveChatWorkspace(data.workspaceInfo);
}
// Ingest sessions
for (const session of data.sessions) {
await this.storageProvider.saveChatSession(session);
progress.progress.processedSessions++;
}
// Ingest messages
if (data.messages.length > 0) {
await this.storageProvider.saveChatMessages(data.messages);
progress.progress.processedMessages = data.messages.length;
}
// Update final progress
progress.progress.percentage = 100;
progress.status = 'completed';
progress.completedAt = new Date().toISOString();
progress.results = {
importedSessions: data.sessions.length,
importedMessages: data.messages.length,
linkedSessions: 0, // TODO: Implement auto-linking
errors: 0,
warnings: [],
};
console.log(`[ChatHub] Successfully processed bulk data from ${data.source}`);
return progress;
}
catch (error) {
console.error('[ChatHub] Error processing bulk data:', error);
progress.status = 'failed';
progress.completedAt = new Date().toISOString();
progress.error = {
message: error instanceof Error ? error.message : 'Unknown error',
details: { stack: error instanceof Error ? error.stack : undefined },
};
throw error;
}
}
async getImportProgress(importId) {
return this.activeImports.get(importId) || null;
}
async suggestChatDevlogLinks(sessionId, minConfidence = 0.5) {
// Simplified implementation - can be enhanced later
console.log(`[ChatHub] Suggesting links for session ${sessionId || 'all'} with min confidence ${minConfidence}`);
// TODO: Implement sophisticated chat-devlog linking logic
// For now, return empty array - this will be enhanced with proper analysis
return [];
}
async autoLinkSessions(sessionIds, threshold = 0.8) {
// Simplified implementation - can be enhanced later
console.log(`[ChatHub] Auto-linking ${sessionIds.length} sessions with threshold ${threshold}`);
// TODO: Implement sophisticated auto-linking logic
// For now, return empty array - this will be enhanced with proper analysis
return [];
}
// Helper methods
generateImportId() {
return `chathub_${Date.now()}_${Math.random().toString(36).substring(2, 9)}`;
}
}