From c218db5047d714c08010c9c665790c1768e9bd82 Mon Sep 17 00:00:00 2001 From: Zomatree Date: Fri, 30 Dec 2022 22:44:36 +0000 Subject: [PATCH] add push event --- .../routes/webhooks/webhook_execute_github.rs | 111 ++++++++++++++++-- 1 file changed, 99 insertions(+), 12 deletions(-) diff --git a/crates/delta/src/routes/webhooks/webhook_execute_github.rs b/crates/delta/src/routes/webhooks/webhook_execute_github.rs index 4d5276be..3a55c5f3 100644 --- a/crates/delta/src/routes/webhooks/webhook_execute_github.rs +++ b/crates/delta/src/routes/webhooks/webhook_execute_github.rs @@ -127,7 +127,7 @@ pub struct GithubRepository { watchers_count: Option, size: Option, default_branch: Option, - open_issues_count: Option, + open_issues_count: Option, is_template: Option, topics: Option>, has_issues: Option, @@ -139,16 +139,16 @@ pub struct GithubRepository { archived: Option, disabled: Option, visibility: Option, - pushed_at: Option, - created_at: Option, + pushed_at: Option, + created_at: Option, updated_at: Option, - permissions: GithubRepositoryPermissions, + permissions: Option, role_name: Option, temp_clone_token: Option, delete_branch_on_merge: Option, subscribers_count: Option, network_count: Option, - code_of_conduct: GithubRepositoryCodeOfConduct, + code_of_conduct: Option, license: Option, forks: Option, open_issues: Option, @@ -158,17 +158,55 @@ pub struct GithubRepository { security_and_analysis: Option } + #[derive(Serialize, Deserialize, Debug, JsonSchema)] -#[serde(rename_all = "lowercase")] +pub struct CommitAuthor { + date: Option, + email: Option, + name: String, + username: Option +} + +#[derive(Serialize, Deserialize, Debug, JsonSchema)] +pub struct GithubCommit { + added: Option>, + author: CommitAuthor, + committer: CommitAuthor, + distinct: bool, + id: String, + message: String, + modified: Option>, + removed: Option>, + timestamp: String, + tree_id: String, + url: String +} + +#[derive(Serialize, Deserialize, Debug, JsonSchema)] +#[serde(rename_all = "lowercase", tag = "type")] pub enum BaseEvent { Star { starred_at: Option, + }, + Ping {}, + Push { + after: String, + base_ref: Option, + before: String, + commits: Vec, + compare: String, + created: bool, + deleted: bool, + forced: bool, + head_commit: Option, + pusher: CommitAuthor, + r#ref: String } } #[derive(Serialize, Deserialize, Debug, JsonSchema)] pub struct Event { - action: String, + action: Option, sender: GithubUser, repository: GithubRepository, organization: Option, @@ -228,6 +266,14 @@ impl<'r> OpenApiFromRequest<'r> for EventHeader<'r> { } } +const GREEN: &'static str = "#0f890f"; +const RED: &'static str = "#e73e3e"; +const GREY: &'static str = "#202224"; +const BLUE: &'static str = "#279adc"; +const ORANGE: &'static str = "#d76a34"; +const LIGHT_ORANGE: &'static str = "#d9916d"; +const WHITE: &'static str = "#c3e1c3"; + /// # executes a webhook specific to github /// /// executes a webhook specific to github and sends a message containg the relavent info about the event @@ -242,27 +288,68 @@ pub async fn req(db: &Db, target: Ref, token: String, event: EventHeader<'_>, da let channel = db.fetch_channel(&webhook.channel).await?; - let body = format!(r#"{{"{}": {data}}}"#, &event.0); + let body = format!(r#"{}, "type": "{}"}}"#, &data[0..data.len() - 1], &event.0); log::info!("{body}"); - let Ok(event) = serde_json::from_str::(&body) else { - return Err(Error::InvalidOperation) + let event = match serde_json::from_str::(&body) { + Ok(event) => event, + Err(err) => { + log::error!("{err:?}"); + return Err(Error::InvalidOperation); + } }; + log::info!("{event:?}"); + let sendable_embed = match event.event { BaseEvent::Star { .. } => { - if event.action != "created" { return Ok(()) }; + if !(event.action.as_deref() == Some("created")) { return Ok(()) }; SendableEmbed { title: Some(event.sender.login), description: Some(format!("[[{}] New star added]({})", event.repository.full_name, event.repository.html_url)), - colour: Some("#202224".to_string()), + colour: Some(GREY.to_string()), icon_url: Some(event.sender.avatar_url), url: Some(event.sender.html_url), ..Default::default() } }, + BaseEvent::Push { after, base_ref, before, commits, compare, created, deleted, forced, head_commit, pusher, r#ref } => { + let branch = r#ref.split('/').nth(2).unwrap(); + + if forced { + let description = format!("[{}] Branch {} was force-pushed to {}\n[compare changes]({})", event.repository.full_name, branch, &after[0..=7], compare); + + SendableEmbed { + icon_url: Some(event.sender.avatar_url), + title: Some(event.sender.login), + description: Some(description), + url: Some(event.sender.html_url), + colour: Some(RED.to_string()), + ..Default::default() + } + } else { + let title = format!("[[{}:{}] {} new commit]({})", event.repository.full_name, branch, commits.len(), compare); + let commit_description = commits + .into_iter() + .map(|commit| format!("[`{}`]({}) {} - {}", &commit.id[0..=7], commit.url, commit.message, commit.author.name)) + .collect::>() + .join("\n"); + + SendableEmbed { + title: Some(event.sender.login), + description: Some(format!("{title}\n{commit_description}")), + colour: Some(BLUE.to_string()), + icon_url: Some(event.sender.avatar_url), + url: Some(event.sender.html_url), + ..Default::default() + } + } + } + _ => { + return Ok(()) + } }; let message_id = Ulid::new().to_string();