From cfa5365c097260d253658cac164de6029515e82a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?U=C4=9Fur=20=C3=96zy=C4=B1lmazel?= Date: Fri, 10 Jan 2025 22:08:19 +0300 Subject: [PATCH 1/2] feat: add GitHub star webhook (#1) --- github/github.go | 5 + github/github_test.go | 18 ++++ github/payload.go | 152 ++++++++++++++++++++++++++++++ testdata/github/star-deleted.json | 144 ++++++++++++++++++++++++++++ testdata/github/star.json | 144 ++++++++++++++++++++++++++++ 5 files changed, 463 insertions(+) create mode 100644 testdata/github/star-deleted.json create mode 100644 testdata/github/star.json diff --git a/github/github.go b/github/github.go index 4a9fb14..7411e0c 100644 --- a/github/github.go +++ b/github/github.go @@ -66,6 +66,7 @@ const ( RepositoryEvent Event = "repository" RepositoryVulnerabilityAlertEvent Event = "repository_vulnerability_alert" SecurityAdvisoryEvent Event = "security_advisory" + StarEvent Event = "star" StatusEvent Event = "status" TeamEvent Event = "team" TeamAddEvent Event = "team_add" @@ -322,6 +323,10 @@ func (hook Webhook) Parse(r *http.Request, events ...Event) (interface{}, error) var pl SecurityAdvisoryPayload err = json.Unmarshal([]byte(payload), &pl) return pl, err + case StarEvent: + var pl StarPayload + err = json.Unmarshal([]byte(payload), &pl) + return pl, err case StatusEvent: var pl StatusPayload err = json.Unmarshal([]byte(payload), &pl) diff --git a/github/github_test.go b/github/github_test.go index 39a6203..66e7408 100644 --- a/github/github_test.go +++ b/github/github_test.go @@ -483,6 +483,24 @@ func TestWebhooks(t *testing.T) { "X-Github-Event": []string{"security_advisory"}, }, }, + { + name: "StarEvent", + event: StarEvent, + typ: StarPayload{}, + filename: "../testdata/github/star.json", + headers: http.Header{ + "X-Github-Event": []string{"star"}, + }, + }, + { + name: "StarEventDeleted", + event: StarEvent, + typ: StarPayload{}, + filename: "../testdata/github/star-deleted.json", + headers: http.Header{ + "X-Github-Event": []string{"star"}, + }, + }, { name: "StatusEvent", event: StatusEvent, diff --git a/github/payload.go b/github/payload.go index 2f1cc84..986d8a1 100644 --- a/github/payload.go +++ b/github/payload.go @@ -5858,6 +5858,158 @@ type SecurityAdvisoryPayload struct { } `json:"security_advisory"` } +// StarPayload contains the information for GitHub's star hook event +type StarPayload struct { + Action string `json:"action"` + StarredAt *time.Time `json:"starred_at"` + Repository struct { + ID int64 `json:"id"` + NodeID string `json:"node_id"` + Name string `json:"name"` + FullName string `json:"full_name"` + Private bool `json:"private"` + Owner struct { + Login string `json:"login"` + ID int64 `json:"id"` + NodeID string `json:"node_id"` + AvatarURL string `json:"avatar_url"` + GravatarID string `json:"gravatar_id"` + URL string `json:"url"` + HTMLURL string `json:"html_url"` + FollowersURL string `json:"followers_url"` + FollowingURL string `json:"following_url"` + GistsURL string `json:"gists_url"` + StarredURL string `json:"starred_url"` + SubscriptionsURL string `json:"subscriptions_url"` + OrganizationsURL string `json:"organizations_url"` + ReposURL string `json:"repos_url"` + EventsURL string `json:"events_url"` + ReceivedEventsURL string `json:"received_events_url"` + Type string `json:"type"` + SiteAdmin bool `json:"site_admin"` + } `json:"owner"` + HTMLURL string `json:"html_url"` + Description string `json:"description"` + Fork bool `json:"fork"` + URL string `json:"url"` + ForksURL string `json:"forks_url"` + KeysURL string `json:"keys_url"` + CollaboratorsURL string `json:"collaborators_url"` + TeamsURL string `json:"teams_url"` + HooksURL string `json:"hooks_url"` + IssueEventsURL string `json:"issue_events_url"` + EventsURL string `json:"events_url"` + AssigneesURL string `json:"assignees_url"` + BranchesURL string `json:"branches_url"` + TagsURL string `json:"tags_url"` + BlobsURL string `json:"blobs_url"` + GitTagsURL string `json:"git_tags_url"` + GitRefsURL string `json:"git_refs_url"` + TreesURL string `json:"trees_url"` + StatusesURL string `json:"statuses_url"` + LanguagesURL string `json:"languages_url"` + StargazersURL string `json:"stargazers_url"` + ContributorsURL string `json:"contributors_url"` + SubscribersURL string `json:"subscribers_url"` + SubscriptionURL string `json:"subscription_url"` + CommitsURL string `json:"commits_url"` + GitCommitsURL string `json:"git_commits_url"` + CommentsURL string `json:"comments_url"` + IssueCommentURL string `json:"issue_comment_url"` + ContentsURL string `json:"contents_url"` + CompareURL string `json:"compare_url"` + MergesURL string `json:"merges_url"` + ArchiveURL string `json:"archive_url"` + DownloadsURL string `json:"downloads_url"` + IssuesURL string `json:"issues_url"` + PullsURL string `json:"pulls_url"` + MilestonesURL string `json:"milestones_url"` + NotificationsURL string `json:"notifications_url"` + LabelsURL string `json:"labels_url"` + ReleasesURL string `json:"releases_url"` + DeploymentsURL string `json:"deployments_url"` + CreatedAt time.Time `json:"created_at"` + UpdatedAt time.Time `json:"updated_at"` + PushedAt time.Time `json:"pushed_at"` + GitURL string `json:"git_url"` + SshURL string `json:"ssh_url"` + CloneURL string `json:"clone_url"` + SvnURL string `json:"svn_url"` + Homepage string `json:"homepage"` + Size int `json:"size"` + StargazersCount int `json:"stargazers_count"` + WatchersCount int `json:"watchers_count"` + Language string `json:"language"` + HasIssues bool `json:"has_issues"` + HasProjects bool `json:"has_projects"` + HasDownloads bool `json:"has_downloads"` + HasWiki bool `json:"has_wiki"` + HasPages bool `json:"has_pages"` + HasDiscussions bool `json:"has_discussions"` + ForksCount int `json:"forks_count"` + MirrorURL interface{} `json:"mirror_url"` + Archived bool `json:"archived"` + Disabled bool `json:"disabled"` + OpenIssuesCount int `json:"open_issues_count"` + License interface{} `json:"license"` + AllowForking bool `json:"allow_forking"` + IsTemplate bool `json:"is_template"` + WebCommitSignoffRequired bool `json:"web_commit_signoff_required"` + Topics []string `json:"topics"` + Visibility string `json:"visibility"` + Forks int `json:"forks"` + OpenIssues int `json:"open_issues"` + Watchers int `json:"watchers"` + DefaultBranch string `json:"default_branch"` + } `json:"repository"` + Organization struct { + Login string `json:"login"` + ID int64 `json:"id"` + NodeID string `json:"node_id"` + URL string `json:"url"` + ReposURL string `json:"repos_url"` + EventsURL string `json:"events_url"` + HooksURL string `json:"hooks_url"` + IssuesURL string `json:"issues_url"` + MembersURL string `json:"members_url"` + PublicMembersURL string `json:"public_members_url"` + AvatarURL string `json:"avatar_url"` + Description string `json:"description"` + } `json:"organization"` + Enterprise *struct { + ID int64 `json:"id"` + Slug string `json:"slug"` + Name string `json:"name"` + NodeID string `json:"node_id"` + AvatarURL string `json:"avatar_url"` + Description string `json:"description"` + WebsiteURL string `json:"website_url"` + HtmlURL string `json:"html_url"` + CreatedAt time.Time `json:"created_at"` + UpdatedAt time.Time `json:"updated_at"` + } `json:"enterprise"` + Sender struct { + Login string `json:"login"` + ID int64 `json:"id"` + NodeID string `json:"node_id"` + AvatarURL string `json:"avatar_url"` + GravatarID string `json:"gravatar_id"` + URL string `json:"url"` + HTMLURL string `json:"html_url"` + FollowersURL string `json:"followers_url"` + FollowingURL string `json:"following_url"` + GistsURL string `json:"gists_url"` + StarredURL string `json:"starred_url"` + SubscriptionsURL string `json:"subscriptions_url"` + OrganizationsURL string `json:"organizations_url"` + ReposURL string `json:"repos_url"` + EventsURL string `json:"events_url"` + ReceivedEventsURL string `json:"received_events_url"` + Type string `json:"type"` + SiteAdmin bool `json:"site_admin"` + } `json:"sender"` +} + // StatusPayload contains the information for GitHub's status hook event type StatusPayload struct { ID int64 `json:"id"` diff --git a/testdata/github/star-deleted.json b/testdata/github/star-deleted.json new file mode 100644 index 0000000..4b004de --- /dev/null +++ b/testdata/github/star-deleted.json @@ -0,0 +1,144 @@ +{ + "action": "deleted", + "starred_at": null, + "repository": { + "id": 906427850, + "node_id": "R_kgDONgb9yg", + "name": "devchain-webhook-test-repo", + "full_name": "bilusteknoloji/devchain-webhook-test-repo", + "private": true, + "owner": { + "login": "bilusteknoloji", + "id": 159630054, + "node_id": "O_kgDOCYPC5g", + "avatar_url": "https://avatars.githubusercontent.com/u/159630054?v=4", + "gravatar_id": "", + "url": "https://api.github.com/users/bilusteknoloji", + "html_url": "https://github.com/bilusteknoloji", + "followers_url": "https://api.github.com/users/bilusteknoloji/followers", + "following_url": "https://api.github.com/users/bilusteknoloji/following{/other_user}", + "gists_url": "https://api.github.com/users/bilusteknoloji/gists{/gist_id}", + "starred_url": "https://api.github.com/users/bilusteknoloji/starred{/owner}{/repo}", + "subscriptions_url": "https://api.github.com/users/bilusteknoloji/subscriptions", + "organizations_url": "https://api.github.com/users/bilusteknoloji/orgs", + "repos_url": "https://api.github.com/users/bilusteknoloji/repos", + "events_url": "https://api.github.com/users/bilusteknoloji/events{/privacy}", + "received_events_url": "https://api.github.com/users/bilusteknoloji/received_events", + "type": "Organization", + "user_view_type": "public", + "site_admin": false + }, + "html_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo", + "description": "This is a dummy repo for testing github webhook payload + events", + "fork": false, + "url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo", + "forks_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/forks", + "keys_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/keys{/key_id}", + "collaborators_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/collaborators{/collaborator}", + "teams_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/teams", + "hooks_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/hooks", + "issue_events_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues/events{/number}", + "events_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/events", + "assignees_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/assignees{/user}", + "branches_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/branches{/branch}", + "tags_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/tags", + "blobs_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/blobs{/sha}", + "git_tags_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/tags{/sha}", + "git_refs_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/refs{/sha}", + "trees_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/trees{/sha}", + "statuses_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/statuses/{sha}", + "languages_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/languages", + "stargazers_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/stargazers", + "contributors_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/contributors", + "subscribers_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/subscribers", + "subscription_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/subscription", + "commits_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/commits{/sha}", + "git_commits_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/commits{/sha}", + "comments_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/comments{/number}", + "issue_comment_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues/comments{/number}", + "contents_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/contents/{+path}", + "compare_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/compare/{base}...{head}", + "merges_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/merges", + "archive_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/{archive_format}{/ref}", + "downloads_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/downloads", + "issues_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues{/number}", + "pulls_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/pulls{/number}", + "milestones_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/milestones{/number}", + "notifications_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/notifications{?since,all,participating}", + "labels_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/labels{/name}", + "releases_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/releases{/id}", + "deployments_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/deployments", + "created_at": "2024-12-20T22:20:56Z", + "updated_at": "2025-01-10T17:24:56Z", + "pushed_at": "2025-01-09T10:09:35Z", + "git_url": "git://github.com/bilusteknoloji/devchain-webhook-test-repo.git", + "ssh_url": "git@github.com:bilusteknoloji/devchain-webhook-test-repo.git", + "clone_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo.git", + "svn_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo", + "homepage": null, + "size": 10, + "stargazers_count": 1, + "watchers_count": 1, + "language": null, + "has_issues": true, + "has_projects": false, + "has_downloads": true, + "has_wiki": false, + "has_pages": false, + "has_discussions": false, + "forks_count": 0, + "mirror_url": null, + "archived": false, + "disabled": false, + "open_issues_count": 8, + "license": null, + "allow_forking": false, + "is_template": false, + "web_commit_signoff_required": false, + "topics": [ + + ], + "visibility": "private", + "forks": 0, + "open_issues": 8, + "watchers": 1, + "default_branch": "main", + "custom_properties": { + } + }, + "organization": { + "login": "bilusteknoloji", + "id": 159630054, + "node_id": "O_kgDOCYPC5g", + "url": "https://api.github.com/orgs/bilusteknoloji", + "repos_url": "https://api.github.com/orgs/bilusteknoloji/repos", + "events_url": "https://api.github.com/orgs/bilusteknoloji/events", + "hooks_url": "https://api.github.com/orgs/bilusteknoloji/hooks", + "issues_url": "https://api.github.com/orgs/bilusteknoloji/issues", + "members_url": "https://api.github.com/orgs/bilusteknoloji/members{/member}", + "public_members_url": "https://api.github.com/orgs/bilusteknoloji/public_members{/member}", + "avatar_url": "https://avatars.githubusercontent.com/u/159630054?v=4", + "description": "Software Development and Consultancy" + }, + "sender": { + "login": "vigo", + "id": 82952, + "node_id": "MDQ6VXNlcjgyOTUy", + "avatar_url": "https://avatars.githubusercontent.com/u/82952?v=4", + "gravatar_id": "", + "url": "https://api.github.com/users/vigo", + "html_url": "https://github.com/vigo", + "followers_url": "https://api.github.com/users/vigo/followers", + "following_url": "https://api.github.com/users/vigo/following{/other_user}", + "gists_url": "https://api.github.com/users/vigo/gists{/gist_id}", + "starred_url": "https://api.github.com/users/vigo/starred{/owner}{/repo}", + "subscriptions_url": "https://api.github.com/users/vigo/subscriptions", + "organizations_url": "https://api.github.com/users/vigo/orgs", + "repos_url": "https://api.github.com/users/vigo/repos", + "events_url": "https://api.github.com/users/vigo/events{/privacy}", + "received_events_url": "https://api.github.com/users/vigo/received_events", + "type": "User", + "user_view_type": "public", + "site_admin": false + } +} \ No newline at end of file diff --git a/testdata/github/star.json b/testdata/github/star.json new file mode 100644 index 0000000..5d52ea8 --- /dev/null +++ b/testdata/github/star.json @@ -0,0 +1,144 @@ +{ + "action": "created", + "starred_at": "2025-01-10T17:01:42Z", + "repository": { + "id": 906427850, + "node_id": "R_kgDONgb9yg", + "name": "devchain-webhook-test-repo", + "full_name": "bilusteknoloji/devchain-webhook-test-repo", + "private": true, + "owner": { + "login": "bilusteknoloji", + "id": 159630054, + "node_id": "O_kgDOCYPC5g", + "avatar_url": "https://avatars.githubusercontent.com/u/159630054?v=4", + "gravatar_id": "", + "url": "https://api.github.com/users/bilusteknoloji", + "html_url": "https://github.com/bilusteknoloji", + "followers_url": "https://api.github.com/users/bilusteknoloji/followers", + "following_url": "https://api.github.com/users/bilusteknoloji/following{/other_user}", + "gists_url": "https://api.github.com/users/bilusteknoloji/gists{/gist_id}", + "starred_url": "https://api.github.com/users/bilusteknoloji/starred{/owner}{/repo}", + "subscriptions_url": "https://api.github.com/users/bilusteknoloji/subscriptions", + "organizations_url": "https://api.github.com/users/bilusteknoloji/orgs", + "repos_url": "https://api.github.com/users/bilusteknoloji/repos", + "events_url": "https://api.github.com/users/bilusteknoloji/events{/privacy}", + "received_events_url": "https://api.github.com/users/bilusteknoloji/received_events", + "type": "Organization", + "user_view_type": "public", + "site_admin": false + }, + "html_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo", + "description": "This is a dummy repo for testing github webhook payload + events", + "fork": false, + "url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo", + "forks_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/forks", + "keys_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/keys{/key_id}", + "collaborators_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/collaborators{/collaborator}", + "teams_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/teams", + "hooks_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/hooks", + "issue_events_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues/events{/number}", + "events_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/events", + "assignees_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/assignees{/user}", + "branches_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/branches{/branch}", + "tags_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/tags", + "blobs_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/blobs{/sha}", + "git_tags_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/tags{/sha}", + "git_refs_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/refs{/sha}", + "trees_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/trees{/sha}", + "statuses_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/statuses/{sha}", + "languages_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/languages", + "stargazers_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/stargazers", + "contributors_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/contributors", + "subscribers_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/subscribers", + "subscription_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/subscription", + "commits_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/commits{/sha}", + "git_commits_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/git/commits{/sha}", + "comments_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/comments{/number}", + "issue_comment_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues/comments{/number}", + "contents_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/contents/{+path}", + "compare_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/compare/{base}...{head}", + "merges_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/merges", + "archive_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/{archive_format}{/ref}", + "downloads_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/downloads", + "issues_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/issues{/number}", + "pulls_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/pulls{/number}", + "milestones_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/milestones{/number}", + "notifications_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/notifications{?since,all,participating}", + "labels_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/labels{/name}", + "releases_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/releases{/id}", + "deployments_url": "https://api.github.com/repos/bilusteknoloji/devchain-webhook-test-repo/deployments", + "created_at": "2024-12-20T22:20:56Z", + "updated_at": "2025-01-10T17:01:43Z", + "pushed_at": "2025-01-09T10:09:35Z", + "git_url": "git://github.com/bilusteknoloji/devchain-webhook-test-repo.git", + "ssh_url": "git@github.com:bilusteknoloji/devchain-webhook-test-repo.git", + "clone_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo.git", + "svn_url": "https://github.com/bilusteknoloji/devchain-webhook-test-repo", + "homepage": null, + "size": 10, + "stargazers_count": 2, + "watchers_count": 2, + "language": null, + "has_issues": true, + "has_projects": false, + "has_downloads": true, + "has_wiki": false, + "has_pages": false, + "has_discussions": false, + "forks_count": 0, + "mirror_url": null, + "archived": false, + "disabled": false, + "open_issues_count": 8, + "license": null, + "allow_forking": false, + "is_template": false, + "web_commit_signoff_required": false, + "topics": [ + + ], + "visibility": "private", + "forks": 0, + "open_issues": 8, + "watchers": 2, + "default_branch": "main", + "custom_properties": { + } + }, + "organization": { + "login": "bilusteknoloji", + "id": 159630054, + "node_id": "O_kgDOCYPC5g", + "url": "https://api.github.com/orgs/bilusteknoloji", + "repos_url": "https://api.github.com/orgs/bilusteknoloji/repos", + "events_url": "https://api.github.com/orgs/bilusteknoloji/events", + "hooks_url": "https://api.github.com/orgs/bilusteknoloji/hooks", + "issues_url": "https://api.github.com/orgs/bilusteknoloji/issues", + "members_url": "https://api.github.com/orgs/bilusteknoloji/members{/member}", + "public_members_url": "https://api.github.com/orgs/bilusteknoloji/public_members{/member}", + "avatar_url": "https://avatars.githubusercontent.com/u/159630054?v=4", + "description": "Software Development and Consultancy" + }, + "sender": { + "login": "vigo", + "id": 82952, + "node_id": "MDQ6VXNlcjgyOTUy", + "avatar_url": "https://avatars.githubusercontent.com/u/82952?v=4", + "gravatar_id": "", + "url": "https://api.github.com/users/vigo", + "html_url": "https://github.com/vigo", + "followers_url": "https://api.github.com/users/vigo/followers", + "following_url": "https://api.github.com/users/vigo/following{/other_user}", + "gists_url": "https://api.github.com/users/vigo/gists{/gist_id}", + "starred_url": "https://api.github.com/users/vigo/starred{/owner}{/repo}", + "subscriptions_url": "https://api.github.com/users/vigo/subscriptions", + "organizations_url": "https://api.github.com/users/vigo/orgs", + "repos_url": "https://api.github.com/users/vigo/repos", + "events_url": "https://api.github.com/users/vigo/events{/privacy}", + "received_events_url": "https://api.github.com/users/vigo/received_events", + "type": "User", + "user_view_type": "public", + "site_admin": false + } +} \ No newline at end of file From 642df989c0adb6993b7bb8b8d149d43723916426 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?U=C4=9Fur=20=C3=96zy=C4=B1lmazel?= Date: Mon, 13 Jan 2025 19:29:41 +0300 Subject: [PATCH 2/2] feat: add ping payload for organization --- github/github.go | 22 +++++++++- github/github_test.go | 10 +++++ github/payload.go | 58 +++++++++++++++++++++++++ testdata/github/ping-organization.json | 59 ++++++++++++++++++++++++++ 4 files changed, 148 insertions(+), 1 deletion(-) create mode 100644 testdata/github/ping-organization.json diff --git a/github/github.go b/github/github.go index 7411e0c..f185c54 100644 --- a/github/github.go +++ b/github/github.go @@ -90,6 +90,15 @@ const ( IssueSubtype EventSubtype = "issues" ) +// InstallationTargetType defines a GitHub Hook HTTP Header type +type InstallationTargetType string + +// GitHub hook HTTP header installation target types +const ( + InstallationTargetTypeRepository InstallationTargetType = "repository" + InstallationTargetTypeOrganization InstallationTargetType = "organization" +) + // Option is a configuration option for the webhook type Option func(*Webhook) error @@ -178,6 +187,12 @@ func (hook Webhook) Parse(r *http.Request, events ...Event) (interface{}, error) } } + targetType := InstallationTargetTypeRepository + instTargetType := InstallationTargetType(r.Header.Get("X-GitHub-Hook-Installation-Target-Type")) + if instTargetType == InstallationTargetTypeOrganization { + targetType = InstallationTargetTypeOrganization + } + switch gitHubEvent { case CheckRunEvent: var pl CheckRunPayload @@ -272,7 +287,12 @@ func (hook Webhook) Parse(r *http.Request, events ...Event) (interface{}, error) err = json.Unmarshal([]byte(payload), &pl) return pl, err case PingEvent: - var pl PingPayload + if targetType == InstallationTargetTypeRepository { + var pl PingPayload + err = json.Unmarshal([]byte(payload), &pl) + return pl, err + } + var pl PingOrganizationPayload err = json.Unmarshal([]byte(payload), &pl) return pl, err case ProjectCardEvent: diff --git a/github/github_test.go b/github/github_test.go index 66e7408..366a943 100644 --- a/github/github_test.go +++ b/github/github_test.go @@ -366,6 +366,16 @@ func TestWebhooks(t *testing.T) { "X-Github-Event": []string{"ping"}, }, }, + { + name: "PingEvent", + event: PingEvent, + typ: PingOrganizationPayload{}, + filename: "../testdata/github/ping-organization.json", + headers: http.Header{ + "X-Github-Event": []string{"ping"}, + "X-GitHub-Hook-Installation-Target-Type": []string{"organization"}, + }, + }, { name: "ProjectCardEvent", event: ProjectCardEvent, diff --git a/github/payload.go b/github/payload.go index 986d8a1..49f0976 100644 --- a/github/payload.go +++ b/github/payload.go @@ -3336,6 +3336,64 @@ type PingPayload struct { } `json:"sender"` } +// PingOrganizationPayload contains the information for GitHub's organization ping hook event +type PingOrganizationPayload struct { + Zen string `json:"zen"` + HookID int `json:"hook_id"` + Hook struct { + Type string `json:"type"` + ID int64 `json:"id"` + Name string `json:"name"` + Active bool `json:"active"` + Events []string `json:"events"` + Config struct { + ContentType string `json:"content_type"` + InsecureSSL string `json:"insecure_ssl"` + Secret string `json:"secret"` + URL string `json:"url"` + } `json:"config"` + UpdatedAt time.Time `json:"updated_at"` + CreatedAt time.Time `json:"created_at"` + URL string `json:"url"` + PingURL string `json:"ping_url"` + DeliveriesURL string `json:"deliveries_url"` + } `json:"hook"` + Organization struct { + Login string `json:"login"` + ID int64 `json:"id"` + NodeID string `json:"node_id"` + URL string `json:"url"` + ReposURL string `json:"repos_url"` + EventsURL string `json:"events_url"` + HooksURL string `json:"hooks_url"` + IssuesURL string `json:"issues_url"` + MembersURL string `json:"members_url"` + PublicMembersURL string `json:"public_members_url"` + AvatarURL string `json:"avatar_url"` + Description string `json:"description"` + } `json:"organization"` + Sender struct { + Login string `json:"login"` + ID int64 `json:"id"` + NodeID string `json:"node_id"` + AvatarURL string `json:"avatar_url"` + GravatarID string `json:"gravatar_id"` + URL string `json:"url"` + HTMLURL string `json:"html_url"` + FollowersURL string `json:"followers_url"` + FollowingURL string `json:"following_url"` + GistsURL string `json:"gists_url"` + StarredURL string `json:"starred_url"` + SubscriptionsURL string `json:"subscriptions_url"` + OrganizationsURL string `json:"organizations_url"` + ReposURL string `json:"repos_url"` + EventsURL string `json:"events_url"` + ReceivedEventsURL string `json:"received_events_url"` + Type string `json:"type"` + SiteAdmin bool `json:"site_admin"` + } `json:"sender"` +} + // ProjectCardPayload contains the information for GitHub's project_payload hook event type ProjectCardPayload struct { Action string `json:"action"` diff --git a/testdata/github/ping-organization.json b/testdata/github/ping-organization.json new file mode 100644 index 0000000..96c70e9 --- /dev/null +++ b/testdata/github/ping-organization.json @@ -0,0 +1,59 @@ +{ + "zen": "Avoid administrative distraction.", + "hook_id": 523968606, + "hook": { + "type": "Organization", + "id": 523968606, + "name": "web", + "active": true, + "events": [ + "*" + ], + "config": { + "content_type": "json", + "insecure_ssl": "0", + "secret": "********", + "url": "https://github.devchain.network/v1/webhook/github" + }, + "updated_at": "2025-01-13T07:08:59Z", + "created_at": "2025-01-13T07:08:59Z", + "url": "https://api.github.com/orgs/vbyazilim/hooks/523968606", + "ping_url": "https://api.github.com/orgs/vbyazilim/hooks/523968606/pings", + "deliveries_url": "https://api.github.com/orgs/vbyazilim/hooks/523968606/deliveries" + }, + "organization": { + "login": "vbyazilim", + "id": 34422235, + "node_id": "MDEyOk9yZ2FuaXphdGlvbjM0NDIyMjM1", + "url": "https://api.github.com/orgs/vbyazilim", + "repos_url": "https://api.github.com/orgs/vbyazilim/repos", + "events_url": "https://api.github.com/orgs/vbyazilim/events", + "hooks_url": "https://api.github.com/orgs/vbyazilim/hooks", + "issues_url": "https://api.github.com/orgs/vbyazilim/issues", + "members_url": "https://api.github.com/orgs/vbyazilim/members{/member}", + "public_members_url": "https://api.github.com/orgs/vbyazilim/public_members{/member}", + "avatar_url": "https://avatars.githubusercontent.com/u/34422235?v=4", + "description": "Software Development, Training and Consultancy" + }, + "sender": { + "login": "vigo", + "id": 82952, + "node_id": "MDQ6VXNlcjgyOTUy", + "avatar_url": "https://avatars.githubusercontent.com/u/82952?v=4", + "gravatar_id": "", + "url": "https://api.github.com/users/vigo", + "html_url": "https://github.com/vigo", + "followers_url": "https://api.github.com/users/vigo/followers", + "following_url": "https://api.github.com/users/vigo/following{/other_user}", + "gists_url": "https://api.github.com/users/vigo/gists{/gist_id}", + "starred_url": "https://api.github.com/users/vigo/starred{/owner}{/repo}", + "subscriptions_url": "https://api.github.com/users/vigo/subscriptions", + "organizations_url": "https://api.github.com/users/vigo/orgs", + "repos_url": "https://api.github.com/users/vigo/repos", + "events_url": "https://api.github.com/users/vigo/events{/privacy}", + "received_events_url": "https://api.github.com/users/vigo/received_events", + "type": "User", + "user_view_type": "public", + "site_admin": false + } +} \ No newline at end of file