← back to Dear Bubbe Nextjs
scripts/twitter-report.js
97 lines
#!/usr/bin/env node
const fs = require('fs').promises;
const path = require('path');
const LOGS_DIR = path.join(__dirname, '..', 'logs');
const STATS_FILE = path.join(LOGS_DIR, 'twitter-stats.json');
const POSTED_FILE = path.join(LOGS_DIR, 'posted-tweets.json');
async function generateReport() {
try {
// Load stats
const statsData = await fs.readFile(STATS_FILE, 'utf-8');
const stats = JSON.parse(statsData);
// Load posted tweets
const postedData = await fs.readFile(POSTED_FILE, 'utf-8');
const posted = JSON.parse(postedData);
console.log('═══════════════════════════════════════════════════════════════');
console.log(' 🐦 DEAR BUBBE TWITTER PERFORMANCE REPORT 🐦 ');
console.log('═══════════════════════════════════════════════════════════════');
console.log();
// Overall stats
console.log('📊 OVERALL STATISTICS');
console.log('─────────────────────');
console.log(`📅 Started: ${new Date(stats.startDate).toLocaleString()}`);
console.log(`📝 Total Posts: ${stats.totalPosts}`);
console.log(`🕐 Last Post: ${stats.lastPostTime ? new Date(stats.lastPostTime).toLocaleString() : 'Never'}`);
console.log();
// Daily breakdown
console.log('📈 DAILY BREAKDOWN');
console.log('─────────────────');
const days = Object.keys(stats.dailyPosts).sort();
days.forEach(day => {
const count = stats.dailyPosts[day];
const percentage = (count / 100 * 100).toFixed(1);
const bar = '█'.repeat(Math.floor(count / 2));
console.log(`${day}: ${bar} ${count}/100 (${percentage}%)`);
});
console.log();
// Engagement tracking
console.log('🎯 ENGAGEMENT FEATURES USED');
console.log('────────────────────────');
const withMentions = stats.engagementTracking.filter(e => e.hasMention).length;
const withHashtags = stats.engagementTracking.filter(e => e.hasHashtags).length;
console.log(`@ Celebrity Mentions: ${withMentions} tweets`);
console.log(`# Viral Hashtags: ${withHashtags} tweets`);
console.log();
// Recent tweets
console.log('📝 LAST 5 TWEETS');
console.log('────────────────');
const recentTweets = posted.slice(-5).reverse();
recentTweets.forEach((tweet, i) => {
console.log(`${i + 1}. ${new Date(tweet.timestamp).toLocaleString()}`);
console.log(` ${tweet.text.substring(0, 100)}...`);
console.log(` ID: ${tweet.id}`);
console.log();
});
// Recommendations
console.log('💡 RECOMMENDATIONS');
console.log('─────────────────');
const avgPostsPerDay = stats.totalPosts / Math.max(1, days.length);
if (avgPostsPerDay < 50) {
console.log('⚠️ Posting below 50% capacity - increase frequency');
} else if (avgPostsPerDay < 80) {
console.log('✅ Good posting rate - aim for 80+ posts/day');
} else {
console.log('🌟 Excellent posting rate! Maximizing API usage');
}
if (withMentions < stats.totalPosts * 0.1) {
console.log('📢 Increase celebrity mentions for viral potential');
}
console.log('🎯 Continue posting during peak hours (7-9pm EST)');
console.log('📊 Monitor engagement metrics on Twitter Analytics');
console.log();
console.log('═══════════════════════════════════════════════════════════════');
console.log(' Report generated at', new Date().toLocaleString());
console.log('═══════════════════════════════════════════════════════════════');
} catch (error) {
console.log('No stats available yet. Twitter poster needs to run first.');
console.log('Error:', error.message);
}
}
// Run report
generateReport().catch(console.error);