improvements

This commit is contained in:
2026-03-29 13:40:16 +03:00
parent 644595b6d3
commit 299879a939
27 changed files with 8422 additions and 465 deletions

17
core/Cargo.toml Normal file
View File

@@ -0,0 +1,17 @@
[package]
name = "dreport-core"
version = "0.1.0"
edition = "2024"
[lib]
crate-type = ["cdylib", "rlib"]
[dependencies]
serde = { version = "1", features = ["derive"] }
serde_json = "1"
base64 = "0.22"
wasm-bindgen = "0.2"
[features]
default = []
wasm = []

5
core/src/lib.rs Normal file
View File

@@ -0,0 +1,5 @@
pub mod models;
pub mod template_to_typst;
#[cfg(feature = "wasm")]
mod wasm_api;

297
core/src/models.rs Normal file
View File

@@ -0,0 +1,297 @@
use serde::{Deserialize, Serialize};
// --- Boyut sistemi ---
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(tag = "type")]
pub enum SizeValue {
#[serde(rename = "fixed")]
Fixed { value: f64 },
#[serde(rename = "auto")]
Auto,
#[serde(rename = "fr")]
Fr { value: f64 },
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct SizeConstraint {
pub width: SizeValue,
pub height: SizeValue,
pub min_width: Option<f64>,
pub min_height: Option<f64>,
pub max_width: Option<f64>,
pub max_height: Option<f64>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct PageSettings {
pub width: f64,
pub height: f64,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Padding {
pub top: f64,
pub right: f64,
pub bottom: f64,
pub left: f64,
}
// --- Positioning ---
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(tag = "type")]
pub enum PositionMode {
#[serde(rename = "flow")]
Flow,
#[serde(rename = "absolute")]
Absolute { x: f64, y: f64 },
}
// --- Stil ---
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct TextStyle {
pub font_size: Option<f64>,
pub font_weight: Option<String>,
pub font_family: Option<String>,
pub color: Option<String>,
pub align: Option<String>,
}
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct LineStyle {
pub stroke_color: Option<String>,
pub stroke_width: Option<f64>,
}
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct ContainerStyle {
pub background_color: Option<String>,
pub border_color: Option<String>,
pub border_width: Option<f64>,
pub border_radius: Option<f64>,
pub border_style: Option<String>,
}
// --- Binding ---
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct ScalarBinding {
pub path: String,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct ArrayBinding {
pub path: String,
}
// --- Tablo ---
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct TableColumn {
pub id: String,
pub field: String,
pub title: String,
pub width: SizeValue,
pub align: String,
pub format: Option<String>,
}
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct TableStyle {
pub header_bg: Option<String>,
pub header_color: Option<String>,
pub zebra_odd: Option<String>,
pub zebra_even: Option<String>,
pub border_color: Option<String>,
pub border_width: Option<f64>,
pub font_size: Option<f64>,
pub header_font_size: Option<f64>,
}
// --- Barcode ---
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct BarcodeStyle {
pub color: Option<String>,
}
// --- Element tipleri ---
#[derive(Debug, Clone, Default, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", default)]
pub struct ImageStyle {
pub object_fit: Option<String>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(tag = "type")]
pub enum TemplateElement {
#[serde(rename = "container")]
Container(ContainerElement),
#[serde(rename = "static_text")]
StaticText(StaticTextElement),
#[serde(rename = "text")]
Text(TextElement),
#[serde(rename = "line")]
Line(LineElement),
#[serde(rename = "repeating_table")]
RepeatingTable(RepeatingTableElement),
#[serde(rename = "image")]
Image(ImageElement),
#[serde(rename = "page_number")]
PageNumber(PageNumberElement),
#[serde(rename = "barcode")]
Barcode(BarcodeElement),
}
impl TemplateElement {
pub fn id(&self) -> &str {
match self {
Self::Container(e) => &e.id,
Self::StaticText(e) => &e.id,
Self::Text(e) => &e.id,
Self::Line(e) => &e.id,
Self::RepeatingTable(e) => &e.id,
Self::Image(e) => &e.id,
Self::PageNumber(e) => &e.id,
Self::Barcode(e) => &e.id,
}
}
pub fn position(&self) -> &PositionMode {
match self {
Self::Container(e) => &e.position,
Self::StaticText(e) => &e.position,
Self::Text(e) => &e.position,
Self::Line(e) => &e.position,
Self::RepeatingTable(e) => &e.position,
Self::Image(e) => &e.position,
Self::PageNumber(e) => &e.position,
Self::Barcode(e) => &e.position,
}
}
pub fn size(&self) -> &SizeConstraint {
match self {
Self::Container(e) => &e.size,
Self::StaticText(e) => &e.size,
Self::Text(e) => &e.size,
Self::Line(e) => &e.size,
Self::RepeatingTable(e) => &e.size,
Self::Image(e) => &e.size,
Self::PageNumber(e) => &e.size,
Self::Barcode(e) => &e.size,
}
}
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct ContainerElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub direction: String,
pub gap: f64,
pub padding: Padding,
pub align: String,
pub justify: String,
pub style: ContainerStyle,
pub children: Vec<TemplateElement>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct StaticTextElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub style: TextStyle,
pub content: String,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct TextElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub style: TextStyle,
pub content: Option<String>,
pub binding: ScalarBinding,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct LineElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub style: LineStyle,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct ImageElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub src: Option<String>,
pub binding: Option<ScalarBinding>,
pub style: ImageStyle,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct PageNumberElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub style: TextStyle,
pub format: Option<String>,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct BarcodeElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub format: String, // qr, ean13, ean8, code128, code39
pub value: Option<String>,
pub binding: Option<ScalarBinding>,
pub style: BarcodeStyle,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase")]
pub struct RepeatingTableElement {
pub id: String,
pub position: PositionMode,
pub size: SizeConstraint,
pub data_source: ArrayBinding,
pub columns: Vec<TableColumn>,
pub style: TableStyle,
}
// --- Template ---
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Template {
pub id: String,
pub name: String,
pub page: PageSettings,
pub fonts: Vec<String>,
pub root: ContainerElement,
}

File diff suppressed because it is too large Load Diff

26
core/src/wasm_api.rs Normal file
View File

@@ -0,0 +1,26 @@
use wasm_bindgen::prelude::*;
use crate::models::Template;
use crate::template_to_typst::{self, RenderMode};
/// Template JSON + Data JSON → Typst markup (editör modu, layout query dahil)
#[wasm_bindgen(js_name = "templateToTypstEditor")]
pub fn template_to_typst_editor(template_json: &str, data_json: &str) -> Result<String, JsValue> {
let template: Template = serde_json::from_str(template_json)
.map_err(|e| JsValue::from_str(&format!("Template parse hatasi: {}", e)))?;
let data: serde_json::Value = serde_json::from_str(data_json)
.map_err(|e| JsValue::from_str(&format!("Data parse hatasi: {}", e)))?;
Ok(template_to_typst::template_to_typst(&template, &data, RenderMode::Editor))
}
/// Template JSON + Data JSON → Typst markup (PDF modu, layout query yok)
#[wasm_bindgen(js_name = "templateToTypstPdf")]
pub fn template_to_typst_pdf(template_json: &str, data_json: &str) -> Result<String, JsValue> {
let template: Template = serde_json::from_str(template_json)
.map_err(|e| JsValue::from_str(&format!("Template parse hatasi: {}", e)))?;
let data: serde_json::Value = serde_json::from_str(data_json)
.map_err(|e| JsValue::from_str(&format!("Data parse hatasi: {}", e)))?;
Ok(template_to_typst::template_to_typst(&template, &data, RenderMode::Pdf))
}