aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--examples/server.rs17
-rw-r--r--src/encoding/headers.rs14
-rw-r--r--src/encoding/uri.rs41
-rw-r--r--src/transaction/auth.rs2
4 files changed, 61 insertions, 13 deletions
diff --git a/examples/server.rs b/examples/server.rs
index c973a14..6132dd5 100644
--- a/examples/server.rs
+++ b/examples/server.rs
@@ -47,19 +47,22 @@ async fn handle_client(stream: TcpStream, addr: SocketAddr) -> Result<()> {
let from: From = req.headers.get_res()?;
let to: To = req.headers.get_res()?;
let via: Via = req.headers.get_res()?;
+ let contact: Contact = req.headers.get_res()?;
+ info!("Registered {}", contact.uri.localpart.as_ref().unwrap());
tu.respond(
&req,
Response {
status: Status::Ok,
headers: HeaderMap::new()
- .add(Contact {
- display_name: None,
- uri: Uri {
- content: format!("sip:username@{addr}"),
- },
- params: ";expires=600".to_string(),
- })
+ // .add(Contact {
+ // display_name: None,
+ // uri: Uri {
+ // content: format!("sip:username@{addr}"),
+ // },
+ // params: ";expires=600".to_string(),
+ // })
+ .add(contact)
.add(via)
.add(to)
.add(from)
diff --git a/src/encoding/headers.rs b/src/encoding/headers.rs
index afcfef1..e880739 100644
--- a/src/encoding/headers.rs
+++ b/src/encoding/headers.rs
@@ -166,7 +166,17 @@ impl Display for Contact {
}
impl FromStr for Contact {
type Err = anyhow::Error;
- fn from_str(_s: &str) -> Result<Self, Self::Err> {
- todo!()
+ fn from_str(s: &str) -> Result<Self, Self::Err> {
+ let (display_name, rest) = s.split_once("<").ok_or(anyhow!("malformed contact"))?;
+ let (uri, params) = rest.split_once(">;").ok_or(anyhow!("malformed contact"))?;
+ Ok(Self {
+ display_name: if display_name.is_empty() {
+ None
+ } else {
+ Some(display_name.to_string())
+ },
+ params: params.to_string(),
+ uri: Uri::from_str(uri)?,
+ })
}
}
diff --git a/src/encoding/uri.rs b/src/encoding/uri.rs
index a56cad4..db20700 100644
--- a/src/encoding/uri.rs
+++ b/src/encoding/uri.rs
@@ -1,21 +1,56 @@
+use anyhow::anyhow;
use std::{fmt::Display, str::FromStr};
#[derive(Debug, Clone)]
pub struct Uri {
- pub content: String,
+ pub protocol: String,
+ pub localpart: Option<String>,
+ pub addr: String,
+ pub params: String,
}
impl Display for Uri {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
- write!(f, "{}", self.content)?;
+ let Self {
+ protocol,
+ localpart,
+ addr,
+ params,
+ } = self;
+ write!(
+ f,
+ "{protocol}:{}{addr}{}",
+ if let Some(localpart) = localpart {
+ format!("{localpart}@")
+ } else {
+ "".to_string()
+ },
+ if params.is_empty() {
+ "".to_string()
+ } else {
+ format!(";{params}")
+ }
+ )?;
Ok(())
}
}
impl FromStr for Uri {
type Err = anyhow::Error;
fn from_str(s: &str) -> Result<Self, Self::Err> {
+ eprintln!("{s:?}");
+ let (pr, s) = s.split_once(":").ok_or(anyhow!("protocol sep"))?;
+ let (lp, s) = s.split_once("@").unwrap_or(("", s));
+ let (addr, params) = s.split_once(";").unwrap_or((s, ""));
+
Ok(Self {
- content: s.to_string(),
+ addr: addr.to_owned(),
+ localpart: if lp.is_empty() {
+ None
+ } else {
+ Some(lp.to_string())
+ },
+ params: params.to_string(),
+ protocol: pr.to_string(),
})
}
}
diff --git a/src/transaction/auth.rs b/src/transaction/auth.rs
index 1b3a100..4c46f9b 100644
--- a/src/transaction/auth.rs
+++ b/src/transaction/auth.rs
@@ -27,7 +27,7 @@ impl Authorization {
),
nonce: challenge.nonce,
realm: challenge.realm,
- uri: request.uri.content.clone(),
+ uri: request.uri.to_string(),
username: username.to_string(),
})
}