Added new features to the project

This commit is contained in:
ajaysi
2025-06-30 07:49:48 +05:30
parent bbe56a364d
commit b21cbb68da
48 changed files with 19774 additions and 1889 deletions

View File

@@ -1,16 +1,22 @@
"""
Twitter Dashboard with modern UI components.
Enhanced Twitter Dashboard with modern UI components and improved user experience.
"""
import streamlit as st
from typing import Dict, List
from typing import Dict, List, Optional, Any
import json
from datetime import datetime
from datetime import datetime, timedelta
import plotly.express as px
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import pandas as pd
import numpy as np
from .tweet_generator import smart_tweet_generator
from .twitter_streamlit_ui import (
TwitterDashboard,
FeatureCard,
TweetCard,
TweetForm,
SettingsForm,
Sidebar,
@@ -22,290 +28,702 @@ from .twitter_streamlit_ui import (
get_from_session,
clear_session,
show_success_message,
show_error_message
show_error_message,
show_info_message,
show_warning_message
)
def load_feature_data() -> Dict:
"""Load feature data from a structured format."""
return {
"tweet_generation": {
"title": "Tweet Generation & Optimization",
"icon": "🐦",
"description": "Create and optimize engaging tweets with AI assistance",
"features": [
{
"name": "Smart Tweet Generator",
"description": "Generate multiple tweet variations with optimal character count, hashtags, and emojis",
"status": "active",
"icon": "",
"function": smart_tweet_generator
},
{
"name": "Tweet Performance Predictor",
"description": "Predict engagement rates and best posting times for maximum impact",
"status": "coming_soon",
"icon": "📊"
}
]
},
"content_strategy": {
"title": "Content Strategy Tools",
"icon": "📅",
"description": "Plan and manage your Twitter content strategy effectively",
"features": [
{
"name": "Content Calendar Generator",
"description": "Create weekly/monthly content plans with theme-based scheduling",
"status": "coming_soon",
"icon": "🗓️"
},
{
"name": "Hashtag Strategy Manager",
"description": "Research and manage trending hashtags for better reach",
"status": "coming_soon",
"icon": "#️⃣"
}
]
},
"visual_content": {
"title": "Visual Content Creation",
"icon": "🎨",
"description": "Create engaging visual content for your tweets",
"features": [
{
"name": "Image Generator",
"description": "Create tweet cards, infographics, and quote designs",
"status": "coming_soon",
"icon": "🖼️"
},
{
"name": "Video Content Assistant",
"description": "Generate video scripts and optimize captions",
"status": "coming_soon",
"icon": "🎥"
}
]
},
"engagement": {
"title": "Engagement & Community",
"icon": "🤝",
"description": "Manage and enhance community engagement",
"features": [
{
"name": "Reply Generator",
"description": "Generate context-aware responses with appropriate tone",
"status": "coming_soon",
"icon": "💬"
},
{
"name": "Community Tools",
"description": "Create polls and plan Q&A sessions",
"status": "coming_soon",
"icon": "👥"
}
]
},
"analytics": {
"title": "Analytics & Optimization",
"icon": "📈",
"description": "Track performance and optimize your Twitter strategy",
"features": [
{
"name": "Performance Analytics",
"description": "Track tweet performance and engagement metrics",
"status": "coming_soon",
"icon": "📊"
},
{
"name": "A/B Testing Assistant",
"description": "Test and optimize tweet variations for better results",
"status": "coming_soon",
"icon": "🔍"
}
]
},
"research": {
"title": "Research & Intelligence",
"icon": "🔎",
"description": "Gain insights and stay ahead of trends",
"features": [
{
"name": "Market Research",
"description": "Analyze competitors and track industry trends",
"status": "coming_soon",
"icon": "📊"
},
{
"name": "Content Inspiration",
"description": "Get trending topic suggestions and content ideas",
"status": "coming_soon",
"icon": "💡"
}
]
def apply_modern_styling():
"""Apply modern CSS styling to the dashboard."""
st.markdown("""
<style>
/* Import Google Fonts */
@import url('https://fonts.googleapis.com/css2?family=Inter:wght@300;400;500;600;700&display=swap');
/* Global Styles */
.stApp {
font-family: 'Inter', -apple-system, BlinkMacSystemFont, sans-serif;
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
min-height: 100vh;
}
/* Main Container */
.main-container {
background: rgba(255, 255, 255, 0.95);
backdrop-filter: blur(20px);
border-radius: 20px;
padding: 2rem;
margin: 1rem;
box-shadow: 0 20px 40px rgba(0, 0, 0, 0.1);
}
/* Header Styles */
.dashboard-header {
text-align: center;
margin-bottom: 2rem;
padding: 2rem 0;
background: linear-gradient(135deg, #1DA1F2, #0C85D0);
border-radius: 16px;
color: white;
box-shadow: 0 10px 30px rgba(29, 161, 242, 0.3);
}
.dashboard-title {
font-size: 2.5rem;
font-weight: 700;
margin: 0;
text-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}
.dashboard-subtitle {
font-size: 1.1rem;
opacity: 0.9;
margin-top: 0.5rem;
font-weight: 400;
}
/* Feature Cards */
.feature-card {
background: white;
border-radius: 16px;
padding: 1.5rem;
margin-bottom: 1rem;
box-shadow: 0 8px 25px rgba(0, 0, 0, 0.08);
border: 1px solid rgba(0, 0, 0, 0.05);
transition: all 0.3s ease;
cursor: pointer;
}
.feature-card:hover {
transform: translateY(-5px);
box-shadow: 0 15px 35px rgba(0, 0, 0, 0.15);
}
.feature-icon {
font-size: 2.5rem;
margin-bottom: 1rem;
display: block;
}
.feature-title {
font-size: 1.25rem;
font-weight: 600;
color: #2D3748;
margin-bottom: 0.5rem;
}
.feature-description {
color: #718096;
font-size: 0.95rem;
line-height: 1.5;
margin-bottom: 1rem;
}
.feature-status {
display: inline-block;
padding: 0.25rem 0.75rem;
border-radius: 20px;
font-size: 0.8rem;
font-weight: 500;
text-transform: uppercase;
letter-spacing: 0.5px;
}
.status-active {
background: linear-gradient(135deg, #48BB78, #38A169);
color: white;
}
.status-coming-soon {
background: linear-gradient(135deg, #ED8936, #DD6B20);
color: white;
}
/* Metrics Cards */
.metric-card {
background: white;
border-radius: 12px;
padding: 1.5rem;
text-align: center;
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.08);
border-left: 4px solid #1DA1F2;
}
.metric-value {
font-size: 2rem;
font-weight: 700;
color: #2D3748;
margin-bottom: 0.5rem;
}
.metric-label {
color: #718096;
font-size: 0.9rem;
font-weight: 500;
}
/* Buttons */
.stButton > button {
background: linear-gradient(135deg, #1DA1F2, #0C85D0);
color: white;
border: none;
border-radius: 10px;
padding: 0.75rem 1.5rem;
font-weight: 600;
font-size: 0.95rem;
transition: all 0.3s ease;
box-shadow: 0 4px 15px rgba(29, 161, 242, 0.3);
}
.stButton > button:hover {
transform: translateY(-2px);
box-shadow: 0 8px 25px rgba(29, 161, 242, 0.4);
}
/* Tabs */
.stTabs [data-baseweb="tab-list"] {
gap: 0.5rem;
background: rgba(255, 255, 255, 0.1);
padding: 0.5rem;
border-radius: 12px;
backdrop-filter: blur(10px);
}
.stTabs [data-baseweb="tab"] {
background: transparent;
border-radius: 8px;
color: #4A5568;
font-weight: 500;
padding: 0.75rem 1.5rem;
transition: all 0.3s ease;
}
.stTabs [aria-selected="true"] {
background: white;
color: #1DA1F2;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}
/* Connection Status */
.connection-status {
display: flex;
align-items: center;
gap: 0.5rem;
padding: 1rem;
border-radius: 12px;
margin-bottom: 1.5rem;
font-weight: 500;
}
.status-connected {
background: linear-gradient(135deg, #C6F6D5, #9AE6B4);
color: #22543D;
border: 1px solid #9AE6B4;
}
.status-disconnected {
background: linear-gradient(135deg, #FED7D7, #FEB2B2);
color: #742A2A;
border: 1px solid #FEB2B2;
}
/* Quick Actions */
.quick-actions {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 1rem;
margin: 2rem 0;
}
.quick-action-btn {
background: white;
border: 2px solid #E2E8F0;
border-radius: 12px;
padding: 1.5rem;
text-align: center;
transition: all 0.3s ease;
cursor: pointer;
text-decoration: none;
}
.quick-action-btn:hover {
border-color: #1DA1F2;
transform: translateY(-2px);
box-shadow: 0 8px 25px rgba(29, 161, 242, 0.15);
}
.quick-action-icon {
font-size: 2rem;
margin-bottom: 0.5rem;
display: block;
}
.quick-action-title {
font-weight: 600;
color: #2D3748;
margin-bottom: 0.25rem;
}
.quick-action-desc {
font-size: 0.85rem;
color: #718096;
}
/* Analytics Charts */
.chart-container {
background: white;
border-radius: 16px;
padding: 1.5rem;
margin: 1rem 0;
box-shadow: 0 4px 15px rgba(0, 0, 0, 0.08);
}
/* Responsive Design */
@media (max-width: 768px) {
.main-container {
margin: 0.5rem;
padding: 1rem;
}
.dashboard-title {
font-size: 2rem;
}
.quick-actions {
grid-template-columns: 1fr;
}
}
</style>
""", unsafe_allow_html=True)
def run_dashboard():
"""Main function to run the Twitter dashboard."""
# Initialize dashboard
dashboard = TwitterDashboard()
def render_connection_status():
"""Render Twitter connection status with modern styling."""
# Simulate connection status (replace with real authentication check)
is_connected = get_from_session("twitter_connected", False)
# Load feature data
features = load_feature_data()
# Setup navigation
sidebar = Sidebar(title="Twitter Tools")
sidebar.add_menu_item("Dashboard", "📊", "dashboard")
sidebar.add_menu_item("Tweet Generator", "✍️", "tweet_generator")
sidebar.add_menu_item("Analytics", "📈", "analytics")
sidebar.add_menu_item("Settings", "⚙️", "settings")
# Setup header
header = Header(
title="Twitter AI Writer",
subtitle="Your all-in-one Twitter content creation and management platform"
)
header.add_action("New Tweet", "✏️", lambda: save_to_session("current_page", "tweet_generator"))
header.add_action("Refresh", "🔄", lambda: st.experimental_rerun())
# Setup tabs
tabs = Tabs()
tabs.add_tab("Overview", "📊", lambda: render_overview(features))
tabs.add_tab("Recent Tweets", "🐦", lambda: render_recent_tweets())
tabs.add_tab("Analytics", "📈", lambda: render_analytics())
# Setup breadcrumbs
breadcrumbs = Breadcrumbs()
breadcrumbs.add_item("Home", "dashboard", "🏠")
breadcrumbs.add_item(get_from_session("current_page", "Dashboard").title())
# Render dashboard
dashboard.render()
if is_connected:
user_info = get_from_session("twitter_user", {"name": "Demo User", "handle": "@demo_user"})
st.markdown(f"""
<div class="connection-status status-connected">
<span style="font-size: 1.2rem;">✅</span>
<div>
<strong>Connected as {user_info['name']}</strong>
<div style="font-size: 0.9rem; opacity: 0.8;">{user_info['handle']}</div>
</div>
</div>
""", unsafe_allow_html=True)
else:
st.markdown("""
<div class="connection-status status-disconnected">
<span style="font-size: 1.2rem;">⚠️</span>
<div>
<strong>Twitter Not Connected</strong>
<div style="font-size: 0.9rem; opacity: 0.8;">Connect your account to access all features</div>
</div>
</div>
""", unsafe_allow_html=True)
if st.button("🔗 Connect Twitter Account", key="connect_twitter"):
# Simulate connection (replace with real OAuth flow)
save_to_session("twitter_connected", True)
save_to_session("twitter_user", {"name": "Demo User", "handle": "@demo_user"})
st.rerun()
def render_overview(features: Dict):
"""Render the overview tab content."""
# Feature cards
col1, col2, col3 = st.columns(3)
def render_dashboard_header():
"""Render the modern dashboard header."""
st.markdown("""
<div class="dashboard-header">
<h1 class="dashboard-title">🐦 Twitter AI Dashboard</h1>
<p class="dashboard-subtitle">Create, analyze, and optimize your Twitter content with AI-powered tools</p>
</div>
""", unsafe_allow_html=True)
def render_quick_actions():
"""Render quick action buttons."""
st.markdown("### 🚀 Quick Actions")
col1, col2, col3, col4 = st.columns(4)
with col1:
FeatureCard(
title="Tweet Generator",
description="Create engaging tweets with AI assistance",
icon="✍️",
features=[
{
"name": "AI-Powered",
"description": "Generate tweets using advanced AI"
},
{
"name": "Customizable",
"description": "Adjust tone, length, and style"
}
],
on_click=lambda: save_to_session("current_page", "tweet_generator")
).render()
if st.button("✍️ Create Tweet", use_container_width=True, key="quick_tweet"):
st.session_state.current_page = "tweet_generator"
st.rerun()
with col2:
FeatureCard(
title="Analytics",
description="Track your tweet performance",
icon="📈",
features=[
{
"name": "Engagement",
"description": "Monitor likes, retweets, and replies"
},
{
"name": "Growth",
"description": "Track follower growth over time"
}
]
).render()
if st.button("📊 View Analytics", use_container_width=True, key="quick_analytics"):
st.session_state.current_page = "analytics"
st.rerun()
with col3:
FeatureCard(
title="Settings",
description="Customize your experience",
icon="⚙️",
features=[
{
"name": "Preferences",
"description": "Set your default options"
},
{
"name": "API",
"description": "Configure Twitter API settings"
}
]
).render()
if st.button("📅 Content Calendar", use_container_width=True, key="quick_calendar"):
show_info_message("Content Calendar feature coming soon!")
with col4:
if st.button("⚙️ Settings", use_container_width=True, key="quick_settings"):
st.session_state.current_page = "settings"
st.rerun()
def render_recent_tweets():
"""Render the recent tweets tab content."""
# Tweet form
tweet_form = TweetForm(
on_submit=lambda: handle_tweet_submit()
def render_metrics_overview():
"""Render key metrics overview."""
st.markdown("### 📈 Performance Overview")
# Generate sample metrics (replace with real data)
col1, col2, col3, col4 = st.columns(4)
with col1:
st.markdown("""
<div class="metric-card">
<div class="metric-value">1,234</div>
<div class="metric-label">Total Tweets</div>
</div>
""", unsafe_allow_html=True)
with col2:
st.markdown("""
<div class="metric-card">
<div class="metric-value">45.2K</div>
<div class="metric-label">Total Engagement</div>
</div>
""", unsafe_allow_html=True)
with col3:
st.markdown("""
<div class="metric-card">
<div class="metric-value">3.8%</div>
<div class="metric-label">Engagement Rate</div>
</div>
""", unsafe_allow_html=True)
with col4:
st.markdown("""
<div class="metric-card">
<div class="metric-value">12.5K</div>
<div class="metric-label">Followers</div>
</div>
""", unsafe_allow_html=True)
def render_engagement_chart():
"""Render engagement trends chart."""
st.markdown("### 📊 Engagement Trends")
# Generate sample data (replace with real Twitter data)
dates = pd.date_range(start=datetime.now() - timedelta(days=30), periods=30)
engagement = np.random.normal(100, 20, 30)
engagement = np.maximum(engagement, 0) # Ensure positive values
df = pd.DataFrame({
'Date': dates,
'Engagement': engagement,
'Likes': engagement * 0.6,
'Retweets': engagement * 0.3,
'Replies': engagement * 0.1
})
# Create interactive chart
fig = make_subplots(
rows=2, cols=1,
subplot_titles=('Total Engagement', 'Engagement Breakdown'),
vertical_spacing=0.1,
row_heights=[0.7, 0.3]
)
tweet_form.render()
# Recent tweets
st.markdown("### Recent Tweets")
tweets = get_from_session("tweets", [])
for tweet in tweets:
TweetCard(
content=tweet["content"],
engagement_score=tweet["engagement_score"],
hashtags=tweet["hashtags"],
emojis=tweet["emojis"],
metrics=tweet["metrics"],
on_copy=lambda: copy_tweet(tweet),
on_save=lambda: save_tweet(tweet)
).render()
def render_analytics():
"""Render the analytics tab content."""
st.markdown("### Tweet Analytics")
st.info("Analytics features coming soon!")
def handle_tweet_submit():
"""Handle tweet form submission."""
# Get form data
content = get_from_session("tweet_content")
tone = get_from_session("tone")
length = get_from_session("length")
hashtags = get_from_session("hashtags")
emojis = get_from_session("emojis")
engagement_boost = get_from_session("engagement_boost")
# Main engagement line
fig.add_trace(
go.Scatter(
x=df['Date'],
y=df['Engagement'],
mode='lines+markers',
name='Total Engagement',
line=dict(color='#1DA1F2', width=3),
marker=dict(size=6)
),
row=1, col=1
)
# Create tweet object
tweet = {
"content": content,
"tone": tone,
"length": length,
"hashtags": hashtags,
"emojis": emojis,
"engagement_score": engagement_boost,
"metrics": {
"Engagement": engagement_boost,
"Reach": engagement_boost * 0.8,
"Growth": engagement_boost * 0.6
# Stacked area chart for breakdown
fig.add_trace(
go.Scatter(
x=df['Date'],
y=df['Likes'],
mode='lines',
name='Likes',
fill='tonexty',
line=dict(color='#E53E3E')
),
row=2, col=1
)
fig.add_trace(
go.Scatter(
x=df['Date'],
y=df['Retweets'],
mode='lines',
name='Retweets',
fill='tonexty',
line=dict(color='#38A169')
),
row=2, col=1
)
fig.add_trace(
go.Scatter(
x=df['Date'],
y=df['Replies'],
mode='lines',
name='Replies',
fill='tonexty',
line=dict(color='#D69E2E')
),
row=2, col=1
)
fig.update_layout(
height=500,
showlegend=True,
hovermode='x unified',
plot_bgcolor='rgba(0,0,0,0)',
paper_bgcolor='rgba(0,0,0,0)'
)
fig.update_xaxes(showgrid=True, gridwidth=1, gridcolor='rgba(0,0,0,0.1)')
fig.update_yaxes(showgrid=True, gridwidth=1, gridcolor='rgba(0,0,0,0.1)')
st.plotly_chart(fig, use_container_width=True)
def render_feature_grid():
"""Render the feature grid with modern cards."""
st.markdown("### 🛠️ Available Tools")
features = [
{
"title": "Smart Tweet Generator",
"description": "Create engaging tweets with AI assistance, hashtag suggestions, and emoji optimization",
"icon": "",
"status": "active",
"action": "tweet_generator"
},
{
"title": "Performance Predictor",
"description": "Predict tweet engagement and find optimal posting times",
"icon": "🔮",
"status": "coming_soon",
"action": None
},
{
"title": "Content Calendar",
"description": "Plan and schedule your Twitter content strategy",
"icon": "📅",
"status": "coming_soon",
"action": None
},
{
"title": "Hashtag Research",
"description": "Discover trending hashtags and analyze their performance",
"icon": "#️⃣",
"status": "coming_soon",
"action": None
},
{
"title": "Visual Content",
"description": "Create quote cards, infographics, and visual tweets",
"icon": "🎨",
"status": "coming_soon",
"action": None
},
{
"title": "Analytics Dashboard",
"description": "Deep dive into your Twitter performance metrics",
"icon": "📊",
"status": "coming_soon",
"action": None
}
]
# Create grid layout
cols = st.columns(3)
for i, feature in enumerate(features):
with cols[i % 3]:
status_class = "status-active" if feature["status"] == "active" else "status-coming-soon"
card_html = f"""
<div class="feature-card" onclick="handleFeatureClick('{feature['action']}')">
<span class="feature-icon">{feature['icon']}</span>
<h3 class="feature-title">{feature['title']}</h3>
<p class="feature-description">{feature['description']}</p>
<span class="feature-status {status_class}">{feature['status'].replace('_', ' ')}</span>
</div>
"""
st.markdown(card_html, unsafe_allow_html=True)
# Add button for active features
if feature["status"] == "active" and feature["action"]:
if st.button(f"Launch {feature['title']}", key=f"launch_{i}", use_container_width=True):
st.session_state.current_page = feature["action"]
st.rerun()
def render_recent_activity():
"""Render recent activity feed."""
st.markdown("### 📱 Recent Activity")
# Sample activity data (replace with real data)
activities = [
{"time": "2 hours ago", "action": "Generated tweet", "details": "AI-powered content about social media trends"},
{"time": "5 hours ago", "action": "Analyzed performance", "details": "Tweet received 45 likes and 12 retweets"},
{"time": "1 day ago", "action": "Scheduled tweet", "details": "Content scheduled for optimal posting time"},
{"time": "2 days ago", "action": "Updated hashtags", "details": "Added trending hashtags to improve reach"}
]
for activity in activities:
st.markdown(f"""
<div style="
background: white;
border-radius: 8px;
padding: 1rem;
margin-bottom: 0.5rem;
border-left: 3px solid #1DA1F2;
box-shadow: 0 2px 8px rgba(0,0,0,0.05);
">
<div style="font-weight: 600; color: #2D3748; margin-bottom: 0.25rem;">
{activity['action']}
</div>
<div style="color: #718096; font-size: 0.9rem; margin-bottom: 0.25rem;">
{activity['details']}
</div>
<div style="color: #A0AEC0; font-size: 0.8rem;">
{activity['time']}
</div>
</div>
""", unsafe_allow_html=True)
def run_dashboard():
"""Main function to run the enhanced Twitter dashboard."""
# Apply modern styling
apply_modern_styling()
# Initialize session state
if "current_page" not in st.session_state:
st.session_state.current_page = "dashboard"
# Handle page navigation
if st.session_state.current_page == "tweet_generator":
if st.button("← Back to Dashboard", key="back_to_dashboard"):
st.session_state.current_page = "dashboard"
st.rerun()
smart_tweet_generator()
return
# Main dashboard container
st.markdown('<div class="main-container">', unsafe_allow_html=True)
# Render dashboard header
render_dashboard_header()
# Render connection status
render_connection_status()
# Create main layout
tab1, tab2, tab3 = st.tabs(["🏠 Overview", "📊 Analytics", "⚙️ Settings"])
with tab1:
# Quick actions
render_quick_actions()
# Metrics overview
render_metrics_overview()
# Feature grid
render_feature_grid()
# Recent activity
col1, col2 = st.columns([2, 1])
with col1:
render_engagement_chart()
with col2:
render_recent_activity()
with tab2:
st.markdown("### 📈 Advanced Analytics")
# Time range selector
col1, col2 = st.columns([1, 3])
with col1:
time_range = st.selectbox(
"Time Range",
["Last 7 days", "Last 30 days", "Last 90 days", "Last year"],
index=1
)
# Detailed analytics
render_engagement_chart()
# Performance insights
st.markdown("### 💡 Performance Insights")
insights = [
"Your tweets perform 23% better when posted between 2-4 PM",
"Tweets with 2-3 hashtags get 15% more engagement",
"Visual content increases engagement by 35%",
"Questions in tweets boost replies by 28%"
]
for insight in insights:
st.info(f"💡 {insight}")
with tab3:
st.markdown("### ⚙️ Dashboard Settings")
# Twitter API settings
with st.expander("🔑 Twitter API Configuration", expanded=False):
st.markdown("Configure your Twitter API credentials to enable full functionality.")
api_key = st.text_input("API Key", type="password", help="Your Twitter API key")
api_secret = st.text_input("API Secret", type="password", help="Your Twitter API secret")
access_token = st.text_input("Access Token", type="password", help="Your Twitter access token")
access_token_secret = st.text_input("Access Token Secret", type="password", help="Your Twitter access token secret")
if st.button("Save API Configuration"):
# Save configuration (implement secure storage)
show_success_message("API configuration saved successfully!")
# Dashboard preferences
with st.expander("🎨 Dashboard Preferences", expanded=True):
theme = st.selectbox("Theme", ["Light", "Dark", "Auto"], index=0)
default_tone = st.selectbox("Default Tweet Tone", ["Professional", "Casual", "Humorous", "Inspirational"], index=1)
auto_hashtags = st.checkbox("Auto-suggest hashtags", value=True)
if st.button("Save Preferences"):
show_success_message("Preferences saved successfully!")
# Account management
with st.expander("👤 Account Management", expanded=False):
st.markdown("Manage your connected Twitter accounts and permissions.")
if get_from_session("twitter_connected", False):
st.success("✅ Twitter account connected")
if st.button("Disconnect Account"):
save_to_session("twitter_connected", False)
st.rerun()
else:
st.warning("⚠️ No Twitter account connected")
if st.button("Connect Account"):
save_to_session("twitter_connected", True)
st.rerun()
st.markdown('</div>', unsafe_allow_html=True)
# JavaScript for handling feature clicks
st.markdown("""
<script>
function handleFeatureClick(action) {
if (action && action !== 'null') {
// This would trigger a Streamlit rerun with the selected action
console.log('Feature clicked:', action);
}
# Add to tweets list
tweets = get_from_session("tweets", [])
tweets.append(tweet)
save_to_session("tweets", tweets)
# Show success message
show_success_message("Tweet created successfully!")
def copy_tweet(tweet: Dict):
"""Copy tweet to clipboard."""
show_success_message("Tweet copied to clipboard!")
def save_tweet(tweet: Dict):
"""Save tweet for later."""
show_success_message("Tweet saved!")
}
</script>
""", unsafe_allow_html=True)
if __name__ == "__main__":
run_dashboard()