Browse Source

Use team api for mapping Zulip IDs

Replaces the ad-hoc MAPPING table in source code.
Mark Rousskov 5 years ago
parent
commit
e213af21d5
2 changed files with 20 additions and 11 deletions
  1. 1 1
      src/github.rs
  2. 19 10
      src/zulip.rs

+ 1 - 1
src/github.rs

@@ -41,7 +41,7 @@ impl GithubClient {
         Ok(body)
     }
 
-    async fn json<T>(&self, req: RequestBuilder) -> anyhow::Result<T>
+    pub async fn json<T>(&self, req: RequestBuilder) -> anyhow::Result<T>
     where
         T: serde::de::DeserializeOwned,
     {

+ 19 - 10
src/zulip.rs

@@ -1,5 +1,7 @@
 use crate::db::notifications::delete_ping;
+use crate::github::GithubClient;
 use crate::handlers::Context;
+use anyhow::Context as _;
 
 #[derive(Debug, serde::Deserialize)]
 pub struct Request {
@@ -24,10 +26,14 @@ struct Response<'a> {
     content: &'a str,
 }
 
-// Zulip User ID to GH User ID
-//
-// FIXME: replace with https://github.com/rust-lang/team/pull/222 once it lands
-static MAPPING: &[(usize, i64)] = &[(116122, 5047365), (119235, 1940490)];
+pub async fn to_github_id(client: &GithubClient, zulip_id: usize) -> anyhow::Result<Option<i64>> {
+    let url = format!("{}/zulip-map.json", rust_team_data::v1::BASE_URL);
+    let map: rust_team_data::v1::ZulipMapping = client
+        .json(client.raw().get(&url))
+        .await
+        .context("could not get team data")?;
+    Ok(map.users.get(&zulip_id).map(|v| *v as i64))
+}
 
 pub async fn respond(ctx: &Context, req: Request) -> String {
     let expected_token = std::env::var("ZULIP_TOKEN").expect("`ZULIP_TOKEN` set for authorization");
@@ -40,12 +46,9 @@ pub async fn respond(ctx: &Context, req: Request) -> String {
     }
 
     log::trace!("zulip hook: {:?}", req);
-    let gh_id = match MAPPING
-        .iter()
-        .find(|(zulip, _)| *zulip == req.message.sender_id)
-    {
-        Some((_, gh_id)) => *gh_id,
-        None => {
+    let gh_id = match to_github_id(&ctx.github, req.message.sender_id).await {
+        Ok(Some(gh_id)) => gh_id,
+        Ok(None) => {
             return serde_json::to_string(&Response {
                 content: &format!(
                 "Unknown Zulip user. Please add `zulip-id = {}` to your file in rust-lang/team.",
@@ -53,6 +56,12 @@ pub async fn respond(ctx: &Context, req: Request) -> String {
             })
             .unwrap();
         }
+        Err(e) => {
+            return serde_json::to_string(&Response {
+                content: &format!("Failed to query team API: {:?}", e),
+            })
+            .unwrap();
+        }
     };
 
     match two_words(&req.data) {