forked from
rocksky.app/rocksky
A decentralized music tracking and discovery platform built on AT Protocol 馃幍
1use anyhow::Error;
2
3use crate::types::{Profile, ProfileResponse};
4
5pub async fn did_to_profile(did: &str) -> Result<Profile, Error> {
6 let client = reqwest::Client::new();
7 let response = client
8 .get(format!("https://plc.directory/{}", did))
9 .header("Accept", "application/json")
10 .send()
11 .await?
12 .json::<serde_json::Value>()
13 .await?;
14
15 let handle = response["alsoKnownAs"][0]
16 .as_str()
17 .unwrap_or("")
18 .split("at://")
19 .last()
20 .unwrap_or("");
21
22 let service_endpoint = response["service"][0]["serviceEndpoint"]
23 .as_str()
24 .unwrap_or("");
25
26 if service_endpoint.is_empty() {
27 return Err(Error::msg("Invalid did"));
28 }
29
30 let client = reqwest::Client::new();
31 let mut response = client.get(format!("{}/xrpc/com.atproto.repo.getRecord?repo={}&collection=app.bsky.actor.profile&rkey=self", service_endpoint, did))
32 .header("Accept", "application/json")
33 .send()
34 .await?
35 .json::<ProfileResponse>()
36 .await?;
37
38 response.value.handle = Some(handle.to_string());
39 Ok(response.value)
40}
41
42#[cfg(test)]
43mod tests {
44 use super::*;
45 use anyhow::Result;
46
47 #[tokio::test]
48 async fn test_did_to_profile() -> Result<()> {
49 let did = "did:plc:7vdlgi2bflelz7mmuxoqjfcr";
50 let profile = did_to_profile(did).await?;
51
52 assert_eq!(profile.r#type, "app.bsky.actor.profile");
53 assert!(profile
54 .display_name
55 .map(|s| s.starts_with("Tsiry Sandratraina"))
56 .unwrap_or(false));
57 assert!(profile
58 .handle
59 .map(|s| s == "tsiry-sandratraina.com")
60 .unwrap_or(false));
61
62 let did = "did:plc:fgvx5xqinqoqgpfhito5er3s";
63 let profile = did_to_profile(did).await?;
64
65 assert_eq!(profile.r#type, "app.bsky.actor.profile");
66 assert!(profile
67 .display_name
68 .map(|s| s.starts_with("Lixtrix"))
69 .unwrap_or(false));
70 assert!(profile.handle.map(|s| s == "lixtrix.art").unwrap_or(false));
71
72 let did = "did:plc:d5jvs7uo4z6lw63zzreukgt4";
73 let profile = did_to_profile(did).await?;
74 assert_eq!(profile.r#type, "app.bsky.actor.profile");
75
76 let did = "did:plc:gwxwdfmun3aqaiu5mx7nnyof";
77 let profile = did_to_profile(did).await?;
78 assert_eq!(profile.r#type, "app.bsky.actor.profile");
79
80 Ok(())
81 }
82}