Skip to main content

haystack_core/codecs/
mod.rs

1// Haystack codecs — wire format serialization / deserialization.
2
3pub mod csv;
4pub mod json;
5pub mod rdf;
6pub mod shared;
7pub mod trio;
8pub mod zinc;
9
10use crate::data::HGrid;
11use crate::kinds::Kind;
12
13/// Errors that can occur during encoding or decoding.
14#[derive(Debug, thiserror::Error)]
15pub enum CodecError {
16    #[error("parse error at position {pos}: {message}")]
17    Parse { pos: usize, message: String },
18    #[error("encoding error: {0}")]
19    Encode(String),
20    #[error("unsupported kind for this codec")]
21    UnsupportedKind,
22}
23
24/// Trait for Haystack wire format codecs.
25pub trait Codec: Send + Sync {
26    /// The MIME type for this codec (e.g. `"text/zinc"`).
27    fn mime_type(&self) -> &str;
28
29    /// Encode an HGrid to a string.
30    fn encode_grid(&self, grid: &HGrid) -> Result<String, CodecError>;
31
32    /// Decode a string to an HGrid.
33    fn decode_grid(&self, input: &str) -> Result<HGrid, CodecError>;
34
35    /// Encode a single scalar Kind value to a string.
36    fn encode_scalar(&self, val: &Kind) -> Result<String, CodecError>;
37
38    /// Decode a string to a single scalar Kind value.
39    fn decode_scalar(&self, input: &str) -> Result<Kind, CodecError>;
40}
41
42static ZINC: zinc::ZincCodec = zinc::ZincCodec;
43static TRIO: trio::TrioCodec = trio::TrioCodec;
44static JSON4: json::Json4Codec = json::Json4Codec;
45static JSON3: json::Json3Codec = json::Json3Codec;
46static CSV: csv::CsvCodec = csv::CsvCodec;
47
48/// Look up a codec by MIME type.
49///
50/// Returns a static codec reference for the given MIME type, or `None` if
51/// the MIME type is not supported.
52pub fn codec_for(mime_type: &str) -> Option<&'static dyn Codec> {
53    match mime_type {
54        "text/zinc" => Some(&ZINC),
55        "text/trio" => Some(&TRIO),
56        "application/json" => Some(&JSON4),
57        "application/json;v=3" => Some(&JSON3),
58        "text/csv" => Some(&CSV),
59        _ => None,
60    }
61}