use night_fury_core::BrowserSession;
use serde_json::json;

use night_fury_cli_core::output::{output_err, output_ok, OutputMode};

pub async fn viewport(session: &BrowserSession, parts: &[&str], mode: OutputMode) {
    if parts.len() < 2 {
        output_err(mode, "Usage: viewport <width> <height>");
        return;
    }
    let w: u32 = match parts[0].parse() {
        Ok(v) => v,
        Err(_) => {
            output_err(mode, "width must be an integer");
            return;
        }
    };
    let h: u32 = match parts[1].parse() {
        Ok(v) => v,
        Err(_) => {
            output_err(mode, "height must be an integer");
            return;
        }
    };
    match session.set_viewport(w, h).await {
        Ok(msg) => output_ok(
            mode,
            &msg,
            json!({"action": "viewport", "width": w, "height": h}),
        ),
        Err(e) => output_err(mode, &e.to_string()),
    }
}

pub async fn headers(session: &BrowserSession, parts: &[&str], mode: OutputMode) {
    let raw = parts.join(" ");
    let raw = raw.trim();
    if raw.is_empty() {
        output_err(mode, "Usage: headers <json-object>");
        return;
    }
    let parsed: serde_json::Value = match serde_json::from_str(raw) {
        Ok(v) => v,
        Err(e) => {
            output_err(mode, &format!("Invalid JSON: {e}"));
            return;
        }
    };
    match session.set_extra_headers(parsed.clone()).await {
        Ok(msg) => output_ok(mode, &msg, json!({"action": "headers", "headers": parsed})),
        Err(e) => output_err(mode, &e.to_string()),
    }
}

pub async fn auth(session: &BrowserSession, parts: &[&str], mode: OutputMode) {
    if parts.len() < 2 {
        output_err(mode, "Usage: auth <user> <pass>");
        return;
    }
    let user = parts[0];
    let pass = parts[1..].join(" ");
    match session.authenticate(user, &pass).await {
        Ok(msg) => output_ok(mode, &msg, json!({"action": "auth", "user": user})),
        Err(e) => output_err(mode, &e.to_string()),
    }
}
