use std::fs;
use std::path::{Path, PathBuf};
use std::process::ExitCode;

include!(concat!(env!("OUT_DIR"), "/templates_embedded.rs"));

pub fn run(target: Option<PathBuf>, force: bool) -> ExitCode {
    let target = target.unwrap_or_else(super::util::current_dir);

    if let Err(e) = fs::create_dir_all(&target) {
        eprintln!("error: cannot create {}: {e}", target.display());
        return ExitCode::from(1);
    }

    let mut written = 0u32;
    let mut skipped = 0u32;

    for (rel, bytes) in TEMPLATE_FILES {
        let dest = target.join(rel);
        if dest.exists() && !force {
            skipped += 1;
            println!("skip (exists): {}", dest.display());
            continue;
        }
        if let Some(parent) = dest.parent() {
            if let Err(e) = fs::create_dir_all(parent) {
                eprintln!("error: cannot create {}: {e}", parent.display());
                return ExitCode::from(1);
            }
        }
        if let Err(e) = fs::write(&dest, *bytes) {
            eprintln!("error: cannot write {}: {e}", dest.display());
            return ExitCode::from(1);
        }
        written += 1;
        println!("wrote {}", dest.display());
    }

    println!(
        "\ninit complete: {written} written, {skipped} skipped (use --force to overwrite) in {}",
        target.display()
    );

    // Best-effort first-pass generation so Tier 1 files (`_index.md`,
    // `health.md`) start as real content instead of "NOT YET RUN"
    // placeholders. Failures are soft — the scaffold itself already
    // succeeded; the user can rerun later.
    println!();
    seed_tier1(&target);

    println!("\nNext steps:");
    println!("  1. cd {}", target.display());
    println!("  2. git init && git add . && git commit -m 'koala scaffold'");
    println!("  3. koala-core status   # verify the scaffold is recognised");
    println!("  4. Read CLAUDE.md for the 13 rules and the daily workflow.");
    println!("  5. Open .github/workflows/language-ci.example, pick the snippet");
    println!("     for your language, and rename the file to language-ci.yml.");
    ExitCode::SUCCESS
}

/// Seed `_index.md` / `health.md` so the scaffold doesn't ship
/// "waiting for first CI run" placeholders. Both steps are best-effort
/// — they print a `warn:` line on failure and otherwise stay silent.
fn seed_tier1(target: &Path) {
    match koala_wiki::gen(target) {
        Ok(report) => println!(
            "generated {} Tier 1 wiki file(s) (`koala-core wiki gen`)",
            report.written.len()
        ),
        Err(e) => {
            eprintln!("warn: skipped initial wiki gen ({e}); run `koala-core wiki gen` later")
        }
    }

    let snap = koala_health::collect_snapshot(target);
    let body = koala_health::render_markdown(&snap);
    let health_path = target.join("wiki/health.md");
    if let Some(parent) = health_path.parent() {
        if let Err(e) = fs::create_dir_all(parent) {
            eprintln!("warn: cannot create {}: {e}", parent.display());
            return;
        }
    }
    match fs::write(&health_path, &body) {
        Ok(()) => println!(
            "recorded initial health snapshot ({})",
            health_path.display()
        ),
        Err(e) => eprintln!(
            "warn: skipped initial health snapshot ({e}); run `koala-core health update` later"
        ),
    }
}

#[cfg(test)]
mod tests {
    use super::*;
    use tempfile::TempDir;

    #[test]
    fn seed_overwrites_health_placeholder() {
        // Reproduce the bootstrap regression: scaffold ships a
        // `health.md` placeholder containing "NOT YET RUN" (see
        // `templates/wiki/health.md`); after init runs we expect
        // a real snapshot in its place.
        let tmp = TempDir::new().unwrap();
        let code = run(Some(tmp.path().to_path_buf()), false);
        assert_eq!(code, ExitCode::SUCCESS);

        let health = fs::read_to_string(tmp.path().join("wiki/health.md")).unwrap();
        assert!(
            !health.contains("NOT YET RUN"),
            "health.md should be replaced with a real snapshot, got:\n{health}"
        );
    }

    #[test]
    fn seed_overwrites_features_index_placeholder() {
        // `templates/wiki/features/_index.md` ships with
        // "待 CI 首次跑"; init should regenerate it.
        let tmp = TempDir::new().unwrap();
        let code = run(Some(tmp.path().to_path_buf()), false);
        assert_eq!(code, ExitCode::SUCCESS);

        let idx = fs::read_to_string(tmp.path().join("wiki/features/_index.md")).unwrap();
        assert!(
            !idx.contains("待 CI 首次跑"),
            "features/_index.md should be regenerated, got:\n{idx}"
        );
    }
}
