specta_jsdoc/
lib.rs

1//! [JSDoc](https://jsdoc.app) language exporter.
2#![cfg_attr(docsrs, feature(doc_cfg))]
3#![doc(
4    html_logo_url = "https://github.com/oscartbeaumont/specta/raw/main/.github/logo-128.png",
5    html_favicon_url = "https://github.com/oscartbeaumont/specta/raw/main/.github/logo-128.png"
6)]
7
8use std::{borrow::Cow, path::Path};
9
10use specta::{Language, TypeCollection};
11use specta_typescript::{BigIntExportBehavior, CommentFormatterFn, FormatterFn};
12
13// TODO: Ensure this is up to our `Typescript` exporters standards.
14
15/// JSDoc language exporter.
16#[derive(Debug, Clone, Default)]
17pub struct JSDoc(pub specta_typescript::Typescript);
18
19impl From<specta_typescript::Typescript> for JSDoc {
20    fn from(ts: specta_typescript::Typescript) -> Self {
21        Self(ts)
22    }
23}
24
25impl JSDoc {
26    /// Construct a new JSDoc exporter with the default options configured.
27    pub fn new() -> Self {
28        Default::default()
29    }
30
31    /// Configure a header for the file.
32    ///
33    /// This is perfect for configuring lint ignore rules or other file-level comments.
34    pub fn header(mut self, header: impl Into<Cow<'static, str>>) -> Self {
35        self.0.header = header.into();
36        self
37    }
38
39    /// Configure the BigInt handling behaviour
40    pub fn bigint(mut self, bigint: BigIntExportBehavior) -> Self {
41        self.0.bigint = bigint;
42        self
43    }
44
45    /// Configure a function which is responsible for styling the comments to be exported
46    ///
47    /// Implementations:
48    ///  - [`js_doc`](specta_typescript::lang::ts::js_doc)
49    ///
50    /// Not calling this method will default to the [`js_doc`](specta_typescript::lang::ts::js_doc) exporter.
51    /// `None` will disable comment exporting.
52    /// `Some(exporter)` will enable comment exporting using the provided exporter.
53    pub fn comment_style(mut self, exporter: CommentFormatterFn) -> Self {
54        self.0.comment_exporter = Some(exporter);
55        self
56    }
57
58    /// Configure a function which is responsible for formatting the result file or files
59    ///
60    ///
61    /// Built-in implementations:
62    ///  - [`prettier`](specta_typescript:formatter:::prettier)
63    ///  - [`ESLint`](specta_typescript::formatter::eslint)
64    ///  - [`Biome`](specta_typescript::formatter::biome)e
65    pub fn formatter(mut self, formatter: FormatterFn) -> Self {
66        self.0.formatter = Some(formatter);
67        self
68    }
69}
70
71impl Language for JSDoc {
72    type Error = specta_typescript::ExportError; // TODO: Custom error type
73
74    // TODO: Make this properly export JSDoc
75    fn export(&self, _type_map: &TypeCollection) -> Result<String, Self::Error> {
76        todo!("Coming soon...");
77        // let mut out = self.0.header.to_string();
78        // if !self.0.remove_default_header {
79        //     out += "// This file has been generated by Specta. DO NOT EDIT.\n\n";
80        // }
81
82        // if let Some((ty_name, l0, l1)) = detect_duplicate_type_names(&type_map).into_iter().next() {
83        //     return Err(ExportError::DuplicateTypeName(ty_name, l0, l1));
84        // }
85
86        // for (_, ty) in type_map.iter() {
87        //     is_valid_ty(&ty.inner, &type_map)?;
88
89        //     out += &export_named_datatype(&self.0, ty, &type_map)?;
90        //     out += "\n\n";
91        // }
92
93        // Ok(out)
94    }
95
96    fn format(&self, path: &Path) -> Result<(), Self::Error> {
97        if let Some(formatter) = self.0.formatter {
98            formatter(path)?;
99        }
100        Ok(())
101    }
102}