dataprof_core/partial.rs
1use crate::{classification::DataType, source::FileFormat};
2
3/// Result of fast schema inference — column names paired with inferred data types.
4#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
5pub struct SchemaResult {
6 /// Columns with their inferred types, in source order: CSV/Parquet follow
7 /// the header/schema, JSON/JSONL follow the first record's field order with
8 /// later-only fields appended in first-seen order.
9 pub columns: Vec<ColumnSchema>,
10 /// How many rows were sampled to infer the schema (0 for Parquet metadata).
11 pub rows_sampled: usize,
12 /// Time taken for inference in milliseconds.
13 pub inference_time_ms: u128,
14 /// `true` when the entire file was consumed or schema was read from
15 /// metadata; `false` when inference stopped at the sample-size cap and
16 /// the schema may not have fully stabilized.
17 pub schema_stable: bool,
18}
19
20/// A single column's name and inferred data type.
21#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
22pub struct ColumnSchema {
23 pub name: String,
24 pub data_type: DataType,
25}
26
27/// Lightweight structural summary for a file.
28///
29/// This intentionally sits between `quick_row_count()` / `infer_schema()` and a
30/// full profile: it reports shape and sampled per-column counters, not quality
31/// scores, pattern detection, recommendations, or raw values.
32#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
33pub struct StructureReport {
34 /// Source identifier, currently the file path passed by the caller.
35 pub source: String,
36 /// Detected or explicitly provided file format.
37 pub format: FileFormat,
38 /// Exact or estimated row count for the source.
39 pub row_count: RowCountEstimate,
40 /// Number of rows consumed for the structural column summaries.
41 pub rows_sampled: usize,
42 /// True when the structural pass consumed the whole source.
43 pub source_exhausted: bool,
44 /// True when the structural pass stopped at the row sample cap.
45 pub truncated: bool,
46 /// Human-readable reason for truncation, if any.
47 pub truncation_reason: Option<String>,
48 /// CSV delimiter used for parsing, when applicable.
49 pub delimiter: Option<String>,
50 /// Per-column structural summaries.
51 pub columns: Vec<StructureColumnSummary>,
52 /// Non-fatal caveats, such as estimated row counts.
53 pub warnings: Vec<String>,
54}
55
56/// Sample-derived or metadata-derived structural summary for one column.
57#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
58pub struct StructureColumnSummary {
59 pub name: String,
60 pub data_type: DataType,
61 pub total_count: Option<usize>,
62 pub null_count: Option<usize>,
63 pub null_ratio: Option<f64>,
64 pub unique_count: Option<usize>,
65 pub uniqueness_ratio: Option<f64>,
66 pub distinct_count_approximate: Option<bool>,
67 /// `"sample"` for CSV/JSON/JSONL, `"metadata"` for Parquet.
68 pub provenance: String,
69}
70
71/// Result of a quick row count operation.
72#[derive(Debug, Clone, PartialEq, serde::Serialize, serde::Deserialize)]
73pub struct RowCountEstimate {
74 /// The estimated or exact row count.
75 pub count: u64,
76 /// Whether the count is exact or an estimate.
77 pub exact: bool,
78 /// How the count was obtained.
79 pub method: CountMethod,
80 /// Time taken in milliseconds.
81 pub count_time_ms: u128,
82 /// Approximate 1-sigma relative standard error of the estimate, expressed
83 /// as a fraction of `count` (e.g. `0.02` ≈ ±2%). Populated only for
84 /// sampled estimates where a variance across sampling windows is available;
85 /// `None` for exact counts and when it cannot be estimated.
86 #[serde(default)]
87 pub relative_error: Option<f64>,
88}
89
90/// Method used to obtain the row count.
91#[derive(Debug, Clone, Copy, PartialEq, Eq, serde::Serialize, serde::Deserialize)]
92pub enum CountMethod {
93 /// Read from Parquet file footer metadata (exact, zero row reading).
94 ParquetMetadata,
95 /// Full scan of the file (exact).
96 FullScan,
97 /// Sample-based estimation (approximate).
98 Sampling,
99 /// Full scan of a streaming source (no file metadata available).
100 StreamFullScan,
101}