/* Missing:
download
download_zip
upload
*/

struct Response<T> {
    e: Option<String>,
    o: Option<T>
}

struct LoginResponse {
    otp_needed: bool,
    token: Option<String>
}

struct Session {
    name: String,
    tfa_enabled: bool,
    admin: bool,
    sudo: bool
}

trait Auth {
    fn signup(username: String, password: String) -> Option<String>;
    fn login(username: String, password: String, otp: Option<String>) -> Response<LoginResponse>;
    fn send_recovery_key(username: String);
    fn reset_password(key: String, password: String) -> Option<String>;
    fn change_password(token: String, old_pw: String, new_pw: String) -> Option<String>;
    fn logout(token: String);
    fn logout_all(token: String) -> Option<String>;
    fn tfa_setup_mail(token: String) -> Option<String>;
    fn tfa_setup_totp(token: String) -> Response<String>;
    fn tfa_complete(token: String, otp: String) -> Option<String>;
    fn tfa_disable(token: String) -> Option<String>;
    fn delete_user(token: String) -> Option<String>;
    fn session_info(token: String) -> Response<Session>;
}

struct UserInfo {
    id: u64,
    name: String,
    tfa: bool,
    admin: bool,
    enabled: bool
}

trait Admin {
    fn list_users(token: String) -> Response<[UserInfo]>;
    fn delete_user(token: String, user: u64) -> Option<String>;
    fn logout(token: String, user: u64) -> Option<String>;
    fn disable_tfa(token: String, user: u64) -> Option<String>;
    fn set_admin(token: String, user: u64, admin: bool) -> Option<String>;
    fn set_enabled(token: String, user: u64, enabled: bool) -> Option<String>;
    fn sudo(token: String, user: u64) -> Option<String>;
    fn unsudo(token: String) -> Option<String>;
    fn shutdown(token: String) -> Option<String>;
}

struct Node {
    id: u64,
    name: String,
    file: bool,
    preview: bool,
    parent: Option<u64>,
    size: Option<u64>,
    children: Option<[Node]>
}

struct CreateNodeInfo {
    id: u64,
    exists: bool,
    file: bool
}

struct ZipInfo {
    done: bool,
    progress: u64,
    total: u64
}

struct PathSegment {
    name: String,
    id: Option<u64>
}

trait FS {
    fn get_node(token: String, node: u64) -> Response<Node>;
    fn get_path(token: String, node: u64) -> Response<[PathSegment]>;
    fn get_nodes_size(token: String, nodes: [u64]) -> Response<u64>;
    fn create_node(token: String, file: bool, parent: u64, name: String) -> Response<CreateNodeInfo>;
    fn move_nodes(token: String, nodes: [u64], parent: u64) -> Option<String>;
    fn delete_nodes(token: String, nodes: [u64]) -> Iterator<String>;
    //fn create_zip(token: String, nodes: [u64]) -> Response<u64>;
    //fn zip_progress(token: String, zip_id: u64) -> Response<ZipInfo>;
    fn download_preview(token: String, node: u64) -> Response<String>;
    fn get_mime(token: String, node: u64) -> Response<String>;
}
