#![allow(clippy::unwrap_used)]
#![allow(dead_code)]

use armour::{
    Entry, GetType, Record, RecordStatus, Uid, rapira_record,
    types::{fuid::Fuid, ident::ID, low_id::LowId},
};
use rapira::Rapira;

fn main() -> std::io::Result<()> {
    use ts_rs::TS;

    #[derive(TS, Rapira, GetType)]
    struct User {
        name: String,
    }

    rapira_record!(User, Uid<()>, "test_user");

    #[derive(TS)]
    #[ts(rename_all = "camelCase")]
    struct All {
        pub low_id: LowId<()>,
        pub fuid: Fuid<()>,
        pub id: ID<()>,
        pub uid: Uid<RecordStatus, ()>,
        pub user: User,
        pub entry: Entry<User>,
    }

    LowId::<()>::export_all().unwrap();
    Fuid::<()>::export_all().unwrap();
    ID::<()>::export_all().unwrap();
    Uid::<RecordStatus, ()>::export_all().unwrap();
    User::export_all().unwrap();
    crate::Entry::<User>::export_all().unwrap();
    All::export_all().unwrap();

    Ok(())
}

#[cfg(feature = "ts")]
#[test]
fn gen_types() {
    use rapira::Rapira;
    use serde::Serialize;
    use specta::{export::ts, ts::export};
    use ts::{TypeDef, write_definition_file};

    use crate::{
        Datetime, Duration, Entry, Id, Record, RecordStatus, Uid,
        types::{
            ident::{DefaultHasher, ID},
            optional_id::OptionalId,
        },
    };

    #[derive(TypeDef)]
    struct Api {
        ident: ID<DefaultHasher>,
        id: Id<DefaultHasher>,
        optional: OptionalId<DefaultHasher>,
    }

    #[derive(TypeDef, Serialize, Rapira)]
    struct Value {
        name: String,
        age: u32,
        dt: Datetime,
        speed: Duration,
    }

    rapira_record!(Value, Uid<RecordStatus, DefaultHasher>, "values");

    let mut buf = Vec::new();
    write_definition_file::<_, (Api, Entry<Value>)>(&mut buf, Default::default()).unwrap();
    let s = String::from_utf8(buf).unwrap();

    println!("{s}");

    // let res = export::<ID<DefaultHasher>>();
    // let res = export::<OptionalId<DefaultHasher>>();
    // let res = export::<Id<DefaultHasher>>();
    // println!("{res:?}");
    // assert!(res.is_ok());
    // ts("./types.ts");
}
