datasources-sqlite 0.1.42

SQLite datasource provider
Documentation
use datasources::{Result, TypeConverter, Value};
use uuid::Uuid;

pub struct UuidConverter;

impl TypeConverter<Value, Value> for UuidConverter {
    fn convert(&self, from: &Value) -> Result<Value> {
        Ok(canonical(from))
    }

    fn reverse_convert(&self, to: &Value) -> Result<Value> {
        Ok(canonical(to))
    }
}

fn canonical(value: &Value) -> Value {
    match value {
        Value::Uuid(id) => Value::Text(id.to_string()),
        Value::Text(text) => Uuid::parse_str(text)
            .map(|id| Value::Text(id.to_string()))
            .unwrap_or_else(|_| value.clone()),
        Value::Binary(bytes) => Uuid::from_slice(bytes)
            .map(|id| Value::Text(id.to_string()))
            .unwrap_or_else(|_| value.clone()),
        other => other.clone(),
    }
}

#[cfg(test)]
mod tests {
    use super::*;
    use datasources::Value;

    #[test]
    fn maps_uuid() {
        let converter = UuidConverter;
        let id = "550e8400-e29b-41d4-a716-446655440000";
        let uuid = Uuid::parse_str(id).unwrap();
        let text = Value::from(id);
        assert_eq!(converter.convert(&Value::from(id)).unwrap(), text);
        assert_eq!(converter.convert(&Value::Uuid(uuid)).unwrap(), text);
        assert_eq!(
            converter
                .convert(&Value::Binary(uuid.as_bytes().to_vec()))
                .unwrap(),
            text
        );
        assert_eq!(converter.reverse_convert(&Value::Uuid(uuid)).unwrap(), text);
        assert_eq!(
            converter.convert(&Value::from("nope")).unwrap(),
            Value::from("nope")
        );
        assert_eq!(converter.convert(&Value::Int(1)).unwrap(), Value::Int(1));
        assert_eq!(
            converter.convert(&Value::Bool(true)).unwrap(),
            Value::Bool(true)
        );
        assert_eq!(
            converter.reverse_convert(&Value::Bool(true)).unwrap(),
            Value::Bool(true)
        );
    }
}