TransHub_backend / backup-version-control.js
linguabot's picture
Upload folder using huggingface_hub
da819ac verified
const mongoose = require('mongoose');
const fs = require('fs').promises;
const path = require('path');
// Atlas MongoDB connection string
const MONGODB_URI = 'mongodb+srv://nothingyu:wSg3lbO1PkHiRMq9@sandbox.ecysggv.mongodb.net/test?retryWrites=true&w=majority&appName=sandbox';
// Connect to MongoDB Atlas
const connectDB = async () => {
try {
await mongoose.connect(MONGODB_URI);
console.log('βœ… Connected to MongoDB Atlas');
} catch (error) {
console.error('❌ MongoDB connection error:', error);
process.exit(1);
}
};
// Backup and Version Control System
const backupVersionControl = {
// Create comprehensive backup
async createBackup(customBackupName = null) {
try {
const timestamp = new Date().toISOString().replace(/[:.]/g, '-');
const backupName = customBackupName || `comprehensive-backup-${timestamp}`;
console.log(`πŸ’Ύ Creating comprehensive backup: ${backupName}`);
const collections = ['subtitles', 'sourcetexts', 'submissions', 'users', 'securitylogs'];
const backupData = {
metadata: {
backupName,
timestamp: new Date(),
collections: collections,
totalRecords: 0,
version: '1.0',
createdBy: 'system'
},
data: {}
};
// Export all collections
for (const collection of collections) {
try {
const data = await mongoose.connection.db.collection(collection).find({}).toArray();
backupData.data[collection] = data;
backupData.metadata.totalRecords += data.length;
console.log(` πŸ“¦ Exported ${data.length} records from ${collection}`);
} catch (error) {
console.warn(` ⚠️ Could not export ${collection}:`, error.message);
}
}
// Save backup to file system
const backupDir = path.join(__dirname, 'backups');
await fs.mkdir(backupDir, { recursive: true });
const backupPath = path.join(backupDir, `${backupName}.json`);
await fs.writeFile(backupPath, JSON.stringify(backupData, null, 2));
// Create backup record in database
const backupRecord = {
backupName,
timestamp: new Date(),
collections: collections,
totalRecords: backupData.metadata.totalRecords,
filePath: backupPath,
status: 'created',
createdBy: 'system'
};
// Save to backup collection
const backupCollection = mongoose.connection.db.collection('backups');
await backupCollection.insertOne(backupRecord);
console.log(`βœ… Backup created successfully: ${backupName}`);
console.log(`πŸ“Š Total records: ${backupData.metadata.totalRecords}`);
console.log(`πŸ’Ύ File saved: ${backupPath}`);
return backupName;
} catch (error) {
console.error('❌ Error creating backup:', error);
throw error;
}
},
// Restore from backup
async restoreFromBackup(backupName) {
try {
console.log(`πŸ”„ Restoring from backup: ${backupName}`);
// Load backup file
const backupPath = path.join(__dirname, 'backups', `${backupName}.json`);
const backupData = JSON.parse(await fs.readFile(backupPath, 'utf8'));
console.log(`πŸ“Š Backup metadata:`, backupData.metadata);
// Confirm restoration
console.log('⚠️ This will overwrite existing data. Are you sure? (y/N)');
// In a real implementation, you'd get user confirmation here
// Restore each collection
for (const [collection, data] of Object.entries(backupData.data)) {
try {
// Clear existing data
await mongoose.connection.db.collection(collection).deleteMany({});
// Insert backup data
if (data.length > 0) {
await mongoose.connection.db.collection(collection).insertMany(data);
}
console.log(` βœ… Restored ${data.length} records to ${collection}`);
} catch (error) {
console.error(` ❌ Error restoring ${collection}:`, error.message);
}
}
console.log(`βœ… Restoration completed: ${backupName}`);
} catch (error) {
console.error('❌ Error restoring from backup:', error);
throw error;
}
},
// List available backups
async listBackups() {
try {
console.log('πŸ“‹ Available backups:');
// List from database
const backupCollection = mongoose.connection.db.collection('backups');
const dbBackups = await backupCollection.find({}).sort({ timestamp: -1 }).toArray();
if (dbBackups.length === 0) {
console.log(' No backups found in database');
} else {
console.log(' Database backups:');
dbBackups.forEach(backup => {
console.log(` πŸ“¦ ${backup.backupName} (${backup.totalRecords} records, ${new Date(backup.timestamp).toLocaleString()})`);
});
}
// List from file system
const backupDir = path.join(__dirname, 'backups');
try {
const files = await fs.readdir(backupDir);
const backupFiles = files.filter(file => file.endsWith('.json'));
if (backupFiles.length > 0) {
console.log(' File system backups:');
for (const file of backupFiles) {
const filePath = path.join(backupDir, file);
const stats = await fs.stat(filePath);
console.log(` πŸ’Ύ ${file} (${(stats.size / 1024).toFixed(2)} KB, ${stats.mtime.toLocaleString()})`);
}
}
} catch (error) {
console.log(' No backup directory found');
}
} catch (error) {
console.error('❌ Error listing backups:', error);
}
},
// Version control for content changes
async createVersionControl() {
try {
console.log('πŸ“ Creating version control system...');
const versionControlSchema = new mongoose.Schema({
documentId: { type: String, required: true },
collection: { type: String, required: true },
version: { type: Number, required: true },
changes: mongoose.Schema.Types.Mixed,
timestamp: { type: Date, default: Date.now },
userId: String,
commitMessage: String,
previousVersion: Number,
checksum: String
});
const VersionControl = mongoose.model('VersionControl', versionControlSchema);
// Create indexes for efficient querying
await VersionControl.createIndexes();
console.log('βœ… Version control system created');
return VersionControl;
} catch (error) {
console.error('❌ Error creating version control:', error);
}
},
// Track content changes
async trackChange(collection, documentId, changes, userId, commitMessage) {
try {
const VersionControl = mongoose.model('VersionControl');
// Get current version
const latestVersion = await VersionControl.findOne({
documentId,
collection
}).sort({ version: -1 });
const newVersion = (latestVersion?.version || 0) + 1;
// Create version record
await VersionControl.create({
documentId,
collection,
version: newVersion,
changes,
userId,
commitMessage,
previousVersion: latestVersion?.version || null,
timestamp: new Date()
});
console.log(`πŸ“ Version ${newVersion} created for ${collection}/${documentId}`);
} catch (error) {
console.error('❌ Error tracking change:', error);
}
},
// Get content history
async getContentHistory(collection, documentId) {
try {
const VersionControl = mongoose.model('VersionControl');
const history = await VersionControl.find({
documentId,
collection
}).sort({ version: -1 });
console.log(`πŸ“‹ Version history for ${collection}/${documentId}:`);
history.forEach(version => {
console.log(` v${version.version} (${new Date(version.timestamp).toLocaleString()}) - ${version.commitMessage}`);
});
return history;
} catch (error) {
console.error('❌ Error getting content history:', error);
}
},
// Automated backup scheduling
async scheduleBackups() {
try {
console.log('⏰ Setting up automated backup scheduling...');
const scheduleSchema = new mongoose.Schema({
scheduleType: { type: String, enum: ['daily', 'weekly', 'monthly'], required: true },
lastBackup: Date,
nextBackup: Date,
isActive: { type: Boolean, default: true },
createdBy: String
});
const Schedule = mongoose.model('Schedule', scheduleSchema);
// Create default daily backup schedule
await Schedule.create({
scheduleType: 'daily',
lastBackup: null,
nextBackup: new Date(Date.now() + 24 * 60 * 60 * 1000), // Tomorrow
isActive: true,
createdBy: 'system'
});
console.log('βœ… Automated backup schedule created (daily)');
} catch (error) {
console.error('❌ Error setting up backup scheduling:', error);
}
},
// Verify backup integrity
async verifyBackupIntegrity(backupName) {
try {
console.log(`πŸ” Verifying backup integrity: ${backupName}`);
const backupPath = path.join(__dirname, 'backups', `${backupName}.json`);
const backupData = JSON.parse(await fs.readFile(backupPath, 'utf8'));
let verifiedCount = 0;
let failedCount = 0;
// Verify each collection
for (const [collection, data] of Object.entries(backupData.data)) {
try {
const currentCount = await mongoose.connection.db.collection(collection).countDocuments();
const backupCount = data.length;
if (currentCount === backupCount) {
verifiedCount++;
console.log(` βœ… ${collection}: ${backupCount} records verified`);
} else {
failedCount++;
console.log(` ❌ ${collection}: ${backupCount} in backup, ${currentCount} in database`);
}
} catch (error) {
failedCount++;
console.log(` ❌ ${collection}: verification failed`);
}
}
console.log(`πŸ” Integrity verification complete:`);
console.log(` - Verified: ${verifiedCount} collections`);
console.log(` - Failed: ${failedCount} collections`);
return { verifiedCount, failedCount };
} catch (error) {
console.error('❌ Error verifying backup integrity:', error);
}
}
};
// Main function
const main = async () => {
try {
console.log('πŸš€ Starting backup and version control system...');
// Create comprehensive backup
const backupName = await backupVersionControl.createBackup();
// Create version control system
await backupVersionControl.createVersionControl();
// Set up automated backups
await backupVersionControl.scheduleBackups();
// List available backups
await backupVersionControl.listBackups();
console.log('\nπŸŽ‰ Backup and version control system ready!');
console.log('\nπŸ“‹ Available functions:');
console.log(' - createBackup(): Create new backup');
console.log(' - restoreFromBackup(name): Restore from backup');
console.log(' - listBackups(): List available backups');
console.log(' - trackChange(): Track content changes');
console.log(' - getContentHistory(): Get version history');
console.log(' - verifyBackupIntegrity(): Verify backup integrity');
} catch (error) {
console.error('❌ Error in backup and version control system:', error);
} finally {
await mongoose.disconnect();
console.log('πŸ”Œ Disconnected from MongoDB');
}
};
// Run the system
connectDB().then(() => {
main();
});