1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
use specta::{Language, NamedDataType, TypeMap};
use specta_serde::is_valid_ty;

use crate::{detect_duplicate_type_names, export_named_datatype, ExportConfig, ExportError};

#[derive(Default, Debug)]
#[non_exhaustive]
pub struct Typescript {
    conf: ExportConfig,
}

impl Typescript {
    pub fn with_config(conf: ExportConfig) -> Self {
        Self { conf }
    }
}

impl Language for Typescript {
    type Error = ExportError;

    fn export(&self, type_map: TypeMap) -> Result<String, Self::Error> {
        let mut out = format!(
            "{} // This file has been generated by Specta. DO NOT EDIT.\n\n",
            "" // TODO: self.conf.header
        );

        if let Some((ty_name, l0, l1)) = detect_duplicate_type_names(&type_map).into_iter().next() {
            return Err(ExportError::DuplicateTypeName(ty_name, l0, l1));
        }

        for (_, ty) in type_map.iter() {
            is_valid_ty(&ty.inner, &type_map)?;

            out += &export_named_datatype(&self.conf, ty, &type_map)?;
            out += "\n\n";
        }

        Ok(out)
    }
}