use std::ops::Deref;
pub const MAIN_SEPARATOR: char = '/';
pub fn escape(token: &str, out: &mut String) {
out.truncate(0);
for ch in token.chars() {
match ch {
'~' => { out.push('~'); out.push('0'); },
'/' => { out.push('~'); out.push('1'); },
_ => out.push(ch),
}
}
}
pub fn validate(ptr: &str) -> bool {
let mut o = '?';
for ch in ptr.chars() {
if o == '~' {
match ch { '0' | '1' => {o = '?';}, _ => return false, }
} else if ch == '~' {
o = '~';
}
}
true
}
pub fn is_separator(ch: char) -> bool {
ch == MAIN_SEPARATOR
}
#[derive(Clone)]
pub struct PointerBuf {
inner: String,
}
impl PointerBuf {
pub fn new() -> PointerBuf {
PointerBuf { inner: String::new() }
}
pub fn as_pointer(&self) -> &Pointer {
self
}
pub fn set<T>(&mut self, pointer: &T) where T: AsRef<str> + ?Sized {
self.inner.truncate(0);
self.inner.push_str(pointer.as_ref())
}
pub fn into_string(self) -> String {
self.inner
}
pub fn into_boxed_pointer(self) -> Box<Pointer> {
let rw = Box::into_raw(self.inner.into_boxed_str()) as *mut Pointer;
unsafe { Box::from_raw(rw) }
}
}
impl Deref for PointerBuf {
type Target = Pointer;
fn deref(&self) -> &Self::Target {
unsafe { &*(self.inner.as_ref() as *const str as *const Pointer) }
}
}
impl From<String> for PointerBuf {
fn from(s: String) -> PointerBuf {
PointerBuf { inner: s }
}
}
impl<'a, T> From<&'a T> for PointerBuf where T: AsRef<str> + ?Sized {
fn from(s: &'a T) -> PointerBuf {
PointerBuf::from(s.as_ref().to_string())
}
}
pub struct Pointer {
inner: str,
}
impl Pointer {
}