mod sermon_parser;

use anyhow::{anyhow, Result};
use bulletin_shared::{Config, Bulletin, NewApiClient};
use chrono::{Datelike, Local, NaiveDate, Weekday};
use clap::Parser;
use dialoguer::{Input, theme::ColorfulTheme};
use std::path::PathBuf;

#[derive(Parser, Debug)]
#[command(author, version, about, long_about = None)]
struct Args {
    #[arg(short, long, default_value = "shared/config.toml")]
    config: PathBuf,
    
    #[arg(short, long)]
    date: Option<NaiveDate>,
    
    #[arg(short, long, default_value = "springfield")]
    location: String,
    
    #[arg(short, long)]
    auth_token: Option<String>,
}

fn get_upcoming_saturday(from_date: Option<NaiveDate>) -> NaiveDate {
    let today = from_date.unwrap_or_else(|| Local::now().date_naive());
    let days_until_saturday = match today.weekday() {
        Weekday::Sat => 0,
        Weekday::Sun => 6,
        Weekday::Mon => 5,
        Weekday::Tue => 4,
        Weekday::Wed => 3,
        Weekday::Thu => 2,
        Weekday::Fri => 1,
    };
    
    if days_until_saturday == 0 && from_date.is_none() {
        today + chrono::Duration::days(7)
    } else {
        today + chrono::Duration::days(days_until_saturday as i64)
    }
}

fn prompt_for_missing_value(field_name: &str, default: &str) -> String {
    let theme = ColorfulTheme::default();
    let result: String = Input::with_theme(&theme)
        .with_prompt(format!("{} not found in CSV. Enter name", field_name))
        .default(default.to_string())
        .interact()
        .unwrap_or_else(|_| default.to_string());
    
    if result.is_empty() {
        default.to_string()
    } else {
        result
    }
}

fn format_sabbath_school_section(
    song_leader: &str,
    ss_leader: &str,
    ss_teacher: &str,
    mission_story: &str,
) -> String {
    format!(
        r#"Song Service:<br>
{}<br><br>

Lesson Study:<br>
{}<br><br>

Leadership:<br>
{}<br><br>

Mission Story:<br>
{}<br><br>

Closing Hymn:<br>
{}"#,
        song_leader, ss_teacher, ss_leader, mission_story, ss_leader
    )
}

fn format_divine_worship_section(
    announcements_person: &str,
    responsive_reading: &str,
    opening_song: &str,
    offering_focus: &str,
    offering_person: &str,
    childrens_story_person: &str,
    special_music: &str,
    scripture_reading: &str,
    scripture_reader: &str,
    sermon_title: &str,
    speaker: &str,
    closing_song: &str,
) -> String {
    format!(
        r#"Announcements:<br>
{}<br><br>

Call To Worship:<br>
{}<br><br>

Opening Hymn:<br>
{}<br><br>

Prayer & Praises:<br>
{}<br><br>

Prayer Song:<br>
#671 "As We Come To You in Prayer"<br><br>

Offering:<br>
{}<br>
{}<br><br>

Children's Story:<br>
{}<br><br>

Special Music:<br>
{}<br><br>

Scripture Reading:<br>
{}<br>
{}<br><br>

Sermon:<br>
{}<br><br>

{}<br><br>

Closing Hymn:<br>
{}"#,
        announcements_person,
        responsive_reading,
        opening_song,
        announcements_person,
        offering_focus,
        offering_person,
        childrens_story_person,
        special_music,
        scripture_reading,
        scripture_reader,
        sermon_title,
        speaker,
        closing_song
    )
}

#[tokio::main]
async fn main() -> Result<()> {
    // Load environment variables from .env file
    dotenvy::dotenv().ok();
    
    tracing_subscriber::fmt()
        .with_env_filter("info")
        .init();

    let args = Args::parse();
    
    let _config = Config::from_file(&args.config)?;
    
    let target_saturday = get_upcoming_saturday(args.date);
    println!("--- Creating bulletin for Saturday: {} ---", target_saturday);
    
    println!("\n--- Enter Sermon Details ---");
    println!("Paste sermon details and press Enter twice when done:");
    
    let mut sermon_lines = Vec::new();
    let mut empty_line_count = 0;
    
    loop {
        let mut line = String::new();
        match std::io::stdin().read_line(&mut line) {
            Ok(_) => {
                if line.trim().is_empty() {
                    empty_line_count += 1;
                    if empty_line_count >= 2 {
                        break;
                    }
                } else {
                    empty_line_count = 0;
                    sermon_lines.push(line.trim_end().to_string());
                }
            }
            Err(_) => break,
        }
    }
    
    let sermon_text = sermon_lines.join("\n");
    if sermon_text.trim().is_empty() {
        return Err(anyhow!("No sermon details provided"));
    }
    
    let parsed_sermon = sermon_parser::parse_sermon_details(&sermon_text);
    
    println!("\n--- Creating API client ---");
    let client = if let Some(token) = args.auth_token.or_else(|| std::env::var("BULLETIN_API_TOKEN").ok()) {
        // Use provided token directly
        NewApiClient::new().with_auth_token(token)
    } else {
        // Auto-login with username/password
        let username = std::env::var("BULLETIN_API_USERNAME")
            .map_err(|_| anyhow!("BULLETIN_API_USERNAME environment variable required"))?;
        let password = std::env::var("BULLETIN_API_PASSWORD")
            .map_err(|_| anyhow!("BULLETIN_API_PASSWORD environment variable required"))?;
        
        println!("Logging in with username/password...");
        NewApiClient::new().login(username, password).await?
    };
    
    println!("\nFetching schedule data from API...");
    let weekly_schedule = client.get_schedule_data(target_saturday).await?;
    
    println!("Fetching conference data from API...");
    let conference_data = client.get_conference_data(target_saturday).await?;
    
    let ss_leader = if weekly_schedule.ss_leader.is_empty() {
        prompt_for_missing_value("S.S. Leader", "TBA")
    } else {
        weekly_schedule.ss_leader.clone()
    };
    
    let ss_teacher = if weekly_schedule.ss_teacher.is_empty() {
        prompt_for_missing_value("S.S. Teacher", "TBA")
    } else {
        weekly_schedule.ss_teacher.clone()
    };
    
    let mission_story = if weekly_schedule.mission_story.is_empty() {
        prompt_for_missing_value("Mission Story person", "TBA")
    } else {
        weekly_schedule.mission_story.clone()
    };
    
    let song_leader = if weekly_schedule.song_leader.is_empty() {
        prompt_for_missing_value("Song Leader", "TBA")
    } else {
        weekly_schedule.song_leader.clone()
    };
    
    let announcements_person = if weekly_schedule.announcements.is_empty() {
        prompt_for_missing_value("Announcements person", "TBA")
    } else {
        weekly_schedule.announcements.clone()
    };
    
    let offering_person = if weekly_schedule.offering.is_empty() {
        prompt_for_missing_value("Offering person", "TBA")
    } else {
        weekly_schedule.offering.clone()
    };
    
    let special_music = if weekly_schedule.special_music.is_empty() {
        prompt_for_missing_value("Special Music person", "TBA")
    } else {
        weekly_schedule.special_music.clone()
    };
    
    let speaker = if weekly_schedule.speaker.is_empty() {
        prompt_for_missing_value("Sermon Speaker", "TBA")
    } else {
        weekly_schedule.speaker.clone()
    };
    
    let is_pastor_speaking = speaker.to_lowercase().contains("pastor joseph piresson");
    
    let (scripture_reader, childrens_story_person) = if is_pastor_speaking {
        println!("Pastor Joseph Piresson is speaking - assigning him scripture reading and children's story");
        (speaker.clone(), speaker.clone())
    } else {
        (announcements_person.clone(), announcements_person.clone())
    };
    
    let opening_song = parsed_sermon.get("opening_song")
        .cloned()
        .unwrap_or_else(|| prompt_for_missing_value("Opening Song", "TBA"));
    
    let closing_song = parsed_sermon.get("closing_song")
        .cloned()
        .unwrap_or_else(|| prompt_for_missing_value("Closing Song", "TBA"));
    
    let scripture_reading = parsed_sermon.get("scripture_reading")
        .cloned()
        .unwrap_or_else(|| prompt_for_missing_value("Scripture Reading", "TBA"));
    
    let responsive_reading = parsed_sermon.get("responsive_reading")
        .cloned()
        .unwrap_or_else(|| prompt_for_missing_value("Responsive Reading", "TBA"));
    
    let sermon_title = parsed_sermon.get("sermon_title")
        .cloned()
        .unwrap_or_else(|| "Saturday Worship Service".to_string());
    
    // TODO: Move scripture lookup to API when Bible JSON is added to backend
    let _scripture_full_text = format!("<p>{}</p><p>{} KJV</p>", scripture_reading, scripture_reading);
    
    let sabbath_school_section = format_sabbath_school_section(
        &song_leader,
        &ss_leader,
        &ss_teacher,
        &mission_story,
    );
    
    let divine_worship_section = format_divine_worship_section(
        &announcements_person,
        &responsive_reading,
        &opening_song,
        &conference_data.offering_focus,
        &offering_person,
        &childrens_story_person,
        &special_music,
        &scripture_reading,
        &scripture_reader,
        &sermon_title,
        &speaker,
        &closing_song,
    );
    
    let _sunset_text = format!(
        "Sunset Tonight: {}\n\nSunset Next Friday: {}",
        conference_data.sunset_tonight,
        conference_data.sunset_next_friday
    );
    
    let bulletin = Bulletin {
        id: None,
        date: target_saturday,
        sermon_title: sermon_title.clone(),
        sermon_scripture: scripture_reading,
        sermon_preacher: speaker,
        sermon_opening_hymn: opening_song,
        sermon_closing_hymn: closing_song,
        sabbath_school_section,
        divine_worship_section,
        pdf: None,
        cover_image: None,
        created: None,
        updated: None,
    };
    
    println!("\n--- Creating bulletin in new API ---");
    
    let created_bulletin = client.create_bulletin_from_bulletin(&bulletin).await?;
    
    println!("\nSUCCESS! Created bulletin ID: {}", created_bulletin.id);
    println!("Done! Check your API - bulletin created successfully!");
    
    Ok(())
}