use std::fmt::{self, Debug, Formatter};
use rustc_serialize::{Decoder, Encodable, Encoder};
pub use structured_data::StructuredData;
pub use immutable_data::{ImmutableData, ImmutableDataType};
pub use plain_data::PlainData;
use xor_name::XorName;
#[derive(Hash, PartialEq, Eq, PartialOrd, Ord, Clone, RustcEncodable, RustcDecodable)]
pub enum Data {
Structured(StructuredData),
Immutable(ImmutableData),
Plain(PlainData),
}
impl Data {
pub fn name(&self) -> XorName {
match *self {
Data::Structured(ref data) => data.name(),
Data::Immutable(ref data) => data.name(),
Data::Plain(ref data) => data.name(),
}
}
pub fn payload_size(&self) -> usize {
match *self {
Data::Structured(ref data) => data.payload_size(),
Data::Immutable(ref data) => data.payload_size(),
Data::Plain(ref data) => data.payload_size(),
}
}
}
#[derive(Hash, Debug, PartialEq, Eq, PartialOrd, Ord, Clone, RustcEncodable, RustcDecodable)]
pub enum DataRequest {
Structured(XorName, u64),
Immutable(XorName, ImmutableDataType),
Plain(XorName),
}
impl Debug for Data {
fn fmt(&self, formatter: &mut Formatter) -> fmt::Result {
match *self {
Data::Structured(ref data) => data.fmt(formatter),
Data::Immutable(ref data) => data.fmt(formatter),
Data::Plain(ref data) => data.fmt(formatter),
}
}
}
impl DataRequest {
pub fn name(&self) -> XorName {
match *self {
DataRequest::Structured(name, tag) => StructuredData::compute_name(tag, &name),
DataRequest::Immutable(name, _) | DataRequest::Plain(name) => name,
}
}
}
#[cfg(test)]
mod test {
extern crate rand;
use super::*;
use sodiumoxide::crypto::sign;
use sodiumoxide::crypto::hash::sha512;
use xor_name::XorName;
#[test]
fn data_name() {
let keys = sign::gen_keypair();
let owner_keys = vec![keys.0];
match StructuredData::new(0,
rand::random(),
0,
vec![],
owner_keys.clone(),
vec![],
Some(&keys.1)) {
Ok(structured_data) => {
assert_eq!(structured_data.name(),
Data::Structured(structured_data).name());
}
Err(error) => panic!("Error: {:?}", error),
}
let value = "immutable data value".to_owned().into_bytes();
let immutable_data = ImmutableData::new(ImmutableDataType::Normal, value);
assert_eq!(immutable_data.name(),
Data::Immutable(immutable_data).name());
let name = XorName(sha512::hash(&[]).0);
let plain_data = PlainData::new(name, vec![]);
assert_eq!(plain_data.name(), Data::Plain(plain_data).name());
}
#[test]
fn data_payload_size() {
let keys = ::sodiumoxide::crypto::sign::gen_keypair();
let owner_keys = vec![keys.0];
match StructuredData::new(0,
rand::random(),
0,
vec![],
owner_keys.clone(),
vec![],
Some(&keys.1)) {
Ok(structured_data) => {
assert_eq!(structured_data.payload_size(),
Data::Structured(structured_data).payload_size());
}
Err(error) => panic!("Error: {:?}", error),
}
let value = "immutable data value".to_owned().into_bytes();
let immutable_data = ImmutableData::new(ImmutableDataType::Normal, value);
assert_eq!(immutable_data.payload_size(),
Data::Immutable(immutable_data).payload_size());
let name = XorName(sha512::hash(&[]).0);
let plain_data = PlainData::new(name, vec![]);
assert_eq!(plain_data.payload_size(),
Data::Plain(plain_data).payload_size());
}
#[test]
fn data_request_name() {
let name = XorName(sha512::hash(&[]).0);
let tag = 0;
assert_eq!(StructuredData::compute_name(tag, &name),
DataRequest::Structured(name, tag).name());
let actual_name = DataRequest::Immutable(name, ImmutableDataType::Normal).name();
assert_eq!(name, actual_name);
assert_eq!(name, DataRequest::Plain(name).name());
}
}