mod api;
mod client;
mod stores;
mod types;
pub use api::ApiGenerator;
pub use client::ClientGenerator;
pub use stores::StoreGenerator;
pub use types::TypeGenerator;
use std::path::PathBuf;
use forge_core::schema::SchemaRegistry;
pub struct TypeScriptGenerator {
output_dir: PathBuf,
type_gen: TypeGenerator,
api_gen: ApiGenerator,
client_gen: ClientGenerator,
store_gen: StoreGenerator,
}
impl TypeScriptGenerator {
pub fn new(output_dir: impl Into<PathBuf>) -> Self {
let output_dir = output_dir.into();
Self {
output_dir: output_dir.clone(),
type_gen: TypeGenerator::new(output_dir.clone()),
api_gen: ApiGenerator::new(output_dir.clone()),
client_gen: ClientGenerator::new(output_dir.clone()),
store_gen: StoreGenerator::new(output_dir),
}
}
pub fn generate(&self, registry: &SchemaRegistry) -> Result<(), Error> {
std::fs::create_dir_all(&self.output_dir)?;
let types_content = self.type_gen.generate(registry)?;
std::fs::write(self.output_dir.join("types.ts"), types_content)?;
let api_content = self.api_gen.generate(registry)?;
std::fs::write(self.output_dir.join("api.ts"), api_content)?;
let client_content = self.client_gen.generate()?;
std::fs::write(self.output_dir.join("client.ts"), client_content)?;
let stores_content = self.store_gen.generate()?;
std::fs::write(self.output_dir.join("stores.ts"), stores_content)?;
let index_content = self.generate_index();
std::fs::write(self.output_dir.join("index.ts"), index_content)?;
Ok(())
}
fn generate_index(&self) -> String {
r#"// Auto-generated by FORGE - DO NOT EDIT
export * from './types';
export * from './api';
export * from './client';
export * from './stores';
"#
.to_string()
}
pub fn output_dir(&self) -> &PathBuf {
&self.output_dir
}
}
#[derive(Debug, thiserror::Error)]
pub enum Error {
#[error("IO error: {0}")]
Io(#[from] std::io::Error),
#[error("Serialization error: {0}")]
Serialization(String),
#[error("Template error: {0}")]
Template(String),
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_generator_creation() {
let gen = TypeScriptGenerator::new("/tmp/forge");
assert_eq!(gen.output_dir(), &PathBuf::from("/tmp/forge"));
}
#[test]
fn test_generate_index() {
let gen = TypeScriptGenerator::new("/tmp/forge");
let index = gen.generate_index();
assert!(index.contains("export * from './types'"));
assert!(index.contains("export * from './api'"));
assert!(index.contains("export * from './client'"));
assert!(index.contains("export * from './stores'"));
}
}