use super::conversion_context::ConversionContext;
use super::conversion_string_writer::ConversionStringWriter;
use super::data_conversion_target::DataConversionTarget;
use super::data_converter::DataConverter;
use super::error::DataConversionError;
use crate::datatype::DataType;
#[must_use]
pub struct AdmittedConversion<'session, 'policy, 'source> {
source: DataConverter<'source>,
context: ConversionContext<'session, 'policy>,
}
impl<'session, 'policy, 'source> AdmittedConversion<'session, 'policy, 'source> {
#[inline]
pub(crate) fn new(source: DataConverter<'source>, context: ConversionContext<'session, 'policy>) -> Self {
Self { source, context }
}
#[must_use = "the admitted source reference is returned"]
#[inline]
pub const fn source(&self) -> &DataConverter<'source> {
&self.source
}
#[inline]
pub const fn from_type(&self) -> DataType {
self.context.source_type()
}
#[inline]
pub const fn to_type(&self) -> DataType {
self.context.to_type()
}
#[inline]
pub const fn unsupported(&self) -> DataConversionError {
DataConversionError::unsupported(self.from_type(), self.to_type())
}
#[inline]
pub fn convert<T>(self) -> Result<T, DataConversionError>
where
T: DataConversionTarget,
{
if T::DATA_TYPE != self.to_type() {
return Err(self.unsupported());
}
T::convert(self)
}
#[cfg(feature = "json")]
#[inline]
pub fn decode_json<'de, T>(&mut self, input: &'de [u8]) -> Result<T, DataConversionError>
where
T: serde::Deserialize<'de>,
{
let from = self.from_type();
let to = self.to_type();
self.context
.limits()
.structured()
.max_text_bytes_limit()
.check_usize(input.len())
.map_err(|error| DataConversionError::measured_limit(from, to, error))?;
self.context.decode_json(input)
}
#[cfg(feature = "json")]
#[inline]
pub fn account_json_value(&mut self, value: &serde_json::Value) -> Result<(), DataConversionError> {
self.context.account_json_value(value)
}
#[cfg(feature = "json")]
#[inline]
pub fn encode_json<T>(&mut self, value: &T) -> Result<Vec<u8>, DataConversionError>
where
T: serde::Serialize + ?Sized,
{
self.context.encode_json(value)
}
#[inline]
pub fn write_string<F>(&mut self, render: F) -> Result<String, DataConversionError>
where
F: FnOnce(&mut ConversionStringWriter<'_>) -> Result<(), DataConversionError>,
{
self.context.write_string(render)
}
#[inline]
pub(crate) fn into_parts(self) -> (DataConverter<'source>, ConversionContext<'session, 'policy>) {
(self.source, self.context)
}
}