use rudof_iri::IriS;
use rudof_rdf::rdf_core::term::literal::Lang;
use serde::ser::SerializeMap;
use serde::{Deserialize, Serialize, Serializer};
use std::fmt::Display;
use std::result;
use std::str::FromStr;
#[derive(Debug, PartialEq, Eq, Clone, Deserialize)]
pub enum LiteralExclusion {
Literal(String),
LiteralStem(String),
}
impl Serialize for LiteralExclusion {
fn serialize<S>(&self, serializer: S) -> result::Result<S::Ok, S::Error>
where
S: Serializer,
{
match self {
LiteralExclusion::Literal(lit) => serializer.serialize_str(lit.as_str()),
LiteralExclusion::LiteralStem(stem) => {
let mut map = serializer.serialize_map(Some(2))?;
map.serialize_entry("type", "LiteralStem")?;
map.serialize_entry("stem", stem)?;
map.end()
},
}
}
}
impl Display for LiteralExclusion {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
LiteralExclusion::Literal(lit) => write!(f, "{lit}"),
LiteralExclusion::LiteralStem(stem) => write!(f, "{stem}~"),
}
}
}
#[derive(Debug, PartialEq, Eq, Clone, Deserialize)]
pub enum IriExclusion {
Iri(IriS),
IriStem(IriS),
}
impl Serialize for IriExclusion {
fn serialize<S>(&self, serializer: S) -> result::Result<S::Ok, S::Error>
where
S: Serializer,
{
match self {
IriExclusion::Iri(iri) => serializer.serialize_str(iri.to_string().as_str()),
IriExclusion::IriStem(stem) => {
let mut map = serializer.serialize_map(Some(2))?;
map.serialize_entry("type", "IriStem")?;
map.serialize_entry("stem", stem)?;
map.end()
},
}
}
}
impl Display for IriExclusion {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
IriExclusion::Iri(iri) => write!(f, "{iri}"),
IriExclusion::IriStem(stem) => write!(f, "{stem}~"),
}
}
}
#[derive(Debug, PartialEq, Eq, Clone)]
pub enum LanguageExclusion {
Language(Lang),
LanguageStem(Lang),
}
impl Serialize for LanguageExclusion {
fn serialize<S>(&self, serializer: S) -> result::Result<S::Ok, S::Error>
where
S: Serializer,
{
match self {
LanguageExclusion::Language(lang) => serializer.serialize_str(&lang.to_string()),
LanguageExclusion::LanguageStem(stem) => {
let mut map = serializer.serialize_map(Some(2))?;
map.serialize_entry("type", "LanguageStem")?;
map.serialize_entry("stem", stem)?;
map.end()
},
}
}
}
impl Display for LanguageExclusion {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
LanguageExclusion::Language(lang) => write!(f, "@{lang}"),
LanguageExclusion::LanguageStem(stem) => write!(f, "{stem}~"),
}
}
}
#[derive(Debug, PartialEq, Clone)]
pub enum Exclusion {
LiteralExclusion(LiteralExclusion),
LanguageExclusion(LanguageExclusion),
IriExclusion(IriExclusion),
Untyped(String),
}
#[derive(Debug)]
pub struct SomeNoLitExclusion {
pub exc: Exclusion,
}
#[derive(Debug)]
pub struct SomeNoIriExclusion {
pub exc: Exclusion,
}
#[derive(Debug)]
pub struct SomeNoLanguageExclusion {
pub exc: Exclusion,
}
impl Exclusion {
pub fn parse_literal_exclusions(excs: Vec<Exclusion>) -> Result<Vec<LiteralExclusion>, SomeNoLitExclusion> {
let mut lit_excs = Vec::new();
for e in excs {
match e {
Exclusion::LiteralExclusion(le) => lit_excs.push(le),
Exclusion::Untyped(s) => lit_excs.push(LiteralExclusion::Literal(s)),
other => return Err(SomeNoLitExclusion { exc: other }),
}
}
Ok(lit_excs)
}
pub fn parse_iri_exclusions(excs: Vec<Exclusion>) -> Result<Vec<IriExclusion>, SomeNoIriExclusion> {
let mut iri_excs = Vec::new();
for e in excs {
match &e {
Exclusion::IriExclusion(le) => iri_excs.push(le.clone()),
v @ Exclusion::Untyped(s) => {
let iri = FromStr::from_str(s.as_str()).map_err(|_e| SomeNoIriExclusion { exc: v.clone() })?;
iri_excs.push(IriExclusion::Iri(iri))
},
other => return Err(SomeNoIriExclusion { exc: other.clone() }),
}
}
Ok(iri_excs)
}
pub fn parse_language_exclusions(excs: Vec<Exclusion>) -> Result<Vec<LanguageExclusion>, SomeNoIriExclusion> {
let mut lang_excs = Vec::new();
for exc in excs {
let exc_clone = exc.clone();
match exc {
Exclusion::LanguageExclusion(le) => lang_excs.push(le),
Exclusion::Untyped(s) => {
let lang = Lang::new(s.as_str()).map_err(|_e| SomeNoIriExclusion { exc: exc_clone })?;
lang_excs.push(LanguageExclusion::Language(lang))
},
other => return Err(SomeNoIriExclusion { exc: other }),
}
}
Ok(lang_excs)
}
}
impl Serialize for Exclusion {
fn serialize<S>(&self, serializer: S) -> result::Result<S::Ok, S::Error>
where
S: Serializer,
{
match self {
Exclusion::IriExclusion(_iri) => todo!(),
Exclusion::LiteralExclusion(LiteralExclusion::Literal(_lit)) => {
todo!()
},
Exclusion::LiteralExclusion(LiteralExclusion::LiteralStem(stem)) => {
let mut map = serializer.serialize_map(Some(2))?;
map.serialize_entry("type", "LiteralStem")?;
map.serialize_entry("stem", stem)?;
map.end()
},
Exclusion::LanguageExclusion(stem) => {
let mut map = serializer.serialize_map(Some(2))?;
map.serialize_entry("type", "LanguageStem")?;
map.serialize_entry("stem", stem)?;
map.end()
},
Exclusion::Untyped(str) => serializer.serialize_str(str),
}
}
}
impl Display for Exclusion {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Exclusion::LiteralExclusion(le) => write!(f, "{le}"),
Exclusion::LanguageExclusion(le) => write!(f, "{le}"),
Exclusion::IriExclusion(ie) => write!(f, "{ie}"),
Exclusion::Untyped(s) => write!(f, "{s}"),
}
}
}
#[derive(Debug)]
#[allow(dead_code)]
struct ExclusionTypeError {
value: String,
}