main: resolve webfinger with https uri

This commit is contained in:
Astro 2023-10-31 04:02:31 +01:00
parent 9cfcf60903
commit f9a103de9a
2 changed files with 51 additions and 19 deletions

View file

@ -26,6 +26,30 @@ pub struct Actor {
} }
impl Actor { impl Actor {
pub fn from_uri(mut uri: &str) -> Option<Self> {
if ! uri.starts_with("https://") {
return None;
}
uri = &uri[8..];
let parts = uri.split("/").collect::<Vec<_>>();
if parts.len() != 3 {
return None;
}
let Ok(topic) = urlencoding::decode(parts[2]) else { return None; };
let kind = match parts[1] {
"tag" =>
ActorKind::TagRelay(topic.to_string()),
"instance" =>
ActorKind::InstanceRelay(topic.to_string()),
_ =>
return None,
};
let host = Arc::new(parts[0].to_string());
Some(Actor { host, kind })
}
pub fn uri(&self) -> String { pub fn uri(&self) -> String {
match &self.kind { match &self.kind {
ActorKind::TagRelay(tag) => ActorKind::TagRelay(tag) =>

View file

@ -28,6 +28,7 @@ mod activitypub;
mod actor_cache; mod actor_cache;
mod endpoint; mod endpoint;
use actor::Actor;
use state::State; use state::State;
@ -46,26 +47,33 @@ async fn webfinger(
return StatusCode::NOT_FOUND.into_response(); return StatusCode::NOT_FOUND.into_response();
}, },
}; };
let (target_kind, target_host) = let target = if resource.starts_with("acct:") {
if resource.starts_with("acct:tag-") { let (target_kind, target_host) =
let off = "acct:tag-".len(); if resource.starts_with("acct:tag-") {
let at = resource.find('@'); let off = "acct:tag-".len();
(actor::ActorKind::TagRelay(resource[off..at.unwrap_or(resource.len())].to_string()), let at = resource.find('@');
at.map_or_else(|| state.hostname.clone(), |at| Arc::new(resource[at + 1..].to_string()))) (actor::ActorKind::TagRelay(resource[off..at.unwrap_or(resource.len())].to_string()),
} else if resource.starts_with("acct:instance-") { at.map_or_else(|| state.hostname.clone(), |at| Arc::new(resource[at + 1..].to_string())))
let off = "acct:instance-".len(); } else if resource.starts_with("acct:instance-") {
let at = resource.find('@'); let off = "acct:instance-".len();
(actor::ActorKind::InstanceRelay(resource[off..at.unwrap_or(resource.len())].to_string()), let at = resource.find('@');
at.map_or_else(|| state.hostname.clone(), |at| Arc::new(resource[at + 1..].to_string()))) (actor::ActorKind::InstanceRelay(resource[off..at.unwrap_or(resource.len())].to_string()),
} else { at.map_or_else(|| state.hostname.clone(), |at| Arc::new(resource[at + 1..].to_string())))
track_request("GET", "webfinger", "not_found"); } else {
return StatusCode::NOT_FOUND.into_response(); track_request("GET", "webfinger", "not_found");
}; return StatusCode::NOT_FOUND.into_response();
track_request("GET", "webfinger", "found"); };
let target = actor::Actor { actor::Actor {
host: target_host, host: target_host,
kind: target_kind, kind: target_kind,
}
} else if let Some(target) = Actor::from_uri(resource) {
target
} else {
track_request("GET", "webfinger", "not_found");
return StatusCode::NOT_FOUND.into_response();
}; };
track_request("GET", "webfinger", "found");
Json(json!({ Json(json!({
"subject": &resource, "subject": &resource,
"aliases": &[ "aliases": &[