use crate::codec::ron::RonCodec;
use crate::components::header::HeaderItem;
use crate::components::header::HeaderItems;
use crate::components::header::StyledHeader;
use crate::models;
use leptos::prelude::*;
use serde::Deserialize;
use serde::Serialize;
use std::collections::BTreeSet;
use std::ops::Deref;

#[component]
pub fn Routes() -> impl leptos::IntoView {
    let load = async move {
        // TODO: What to do about this unwrap?
        load_initial_data().await.unwrap()
    };

    let header_items = HeaderItems {
        left: vec![HeaderItem {
            text: "← Ascend".to_string(),
            link: Some("/".to_string()),
        }],
        middle: vec![HeaderItem {
            text: "ROUTES".to_string(),
            link: None,
        }],
        right: vec![],
    };

    leptos::view! {
        <div class="min-w-screen min-h-screen bg-slate-900">
            <StyledHeader items=header_items />

            <div class="container mx-auto mt-2">
                <Await future=load let:data>
                    <Ready data=data.deref().to_owned() />
                </Await>
            </div>
        </div>
    }
}

#[component]
fn Ready(data: InitialData) -> impl leptos::IntoView {
    tracing::debug!("ready");

    let import_from_mini_moonboard = Action::from(ServerAction::<ImportFromMiniMoonboard>::new());

    let onclick = move |_mouse_event| {
        import_from_mini_moonboard.dispatch(ImportFromMiniMoonboard {});
    };

    view! {
        <p>"Import problems from"</p>
        <button on:click=onclick>"Mini Moonboard"</button>
    }
}

#[derive(Debug, Serialize, Deserialize, Clone)]
pub struct InitialData {
    problems: BTreeSet<models::Problem>,
}

#[server]
async fn load_initial_data() -> Result<RonCodec<InitialData>, ServerFnError> {
    todo!()
    // let state = expect_context::<State>();

    // let problems = state
    //     .persistent
    //     .with(|s| {
    //         let problems = &s.problems.problems;
    //         problems.clone()
    //     })
    //     .await;

    // Ok(RonCodec::new(InitialData { problems }))
}

#[server(name = ImportFromMiniMoonboard)]
#[tracing::instrument]
async fn import_from_mini_moonboard() -> Result<(), ServerFnError> {
    use crate::server::config::Config;

    todo!()
    // tracing::info!("Importing mini moonboard problems");

    // let config = expect_context::<Config>();
    // let state = expect_context::<State>();

    // crate::server::operations::import_mini_moonboard_problems(&config, &state).await?;

    // // TODO: Return information about what was done
    // Ok(())
}
