Skip to content

Commit 6c3096d

Browse files
authored
Support issue typed and untyped events (#698)
1 parent b44b70f commit 6c3096d

File tree

9 files changed

+527
-0
lines changed

9 files changed

+527
-0
lines changed

src/Octokit.Webhooks/Events/Issues/IssuesAction.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@ public sealed record IssuesAction : WebhookEventAction
2727

2828
public static readonly IssuesAction Transferred = new(IssuesActionValue.Transferred);
2929

30+
public static readonly IssuesAction Typed = new(IssuesActionValue.Typed);
31+
3032
public static readonly IssuesAction Unassigned = new(IssuesActionValue.Unassigned);
3133

3234
public static readonly IssuesAction Unlabeled = new(IssuesActionValue.Unlabeled);
@@ -35,6 +37,8 @@ public sealed record IssuesAction : WebhookEventAction
3537

3638
public static readonly IssuesAction Unpinned = new(IssuesActionValue.Unpinned);
3739

40+
public static readonly IssuesAction Untyped = new(IssuesActionValue.Untyped);
41+
3842
private IssuesAction(string value)
3943
: base(value)
4044
{

src/Octokit.Webhooks/Events/Issues/IssuesActionValue.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,15 @@ public static class IssuesActionValue
2626

2727
public const string Transferred = "transferred";
2828

29+
public const string Typed = "typed";
30+
2931
public const string Unassigned = "unassigned";
3032

3133
public const string Unlabeled = "unlabeled";
3234

3335
public const string Unlocked = "unlocked";
3436

3537
public const string Unpinned = "unpinned";
38+
39+
public const string Untyped = "untyped";
3640
}
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
namespace Octokit.Webhooks.Events.Issues;
2+
3+
[PublicAPI]
4+
[WebhookActionType(IssuesActionValue.Typed)]
5+
public sealed record IssuesTypedEvent : IssuesEvent
6+
{
7+
[JsonPropertyName("action")]
8+
public override string Action => IssuesAction.Typed;
9+
10+
[JsonPropertyName("type")]
11+
public IssueType? Type { get; init; }
12+
}
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
namespace Octokit.Webhooks.Events.Issues;
2+
3+
[PublicAPI]
4+
[WebhookActionType(IssuesActionValue.Untyped)]
5+
public sealed record IssuesUntypedEvent : IssuesEvent
6+
{
7+
[JsonPropertyName("action")]
8+
public override string Action => IssuesAction.Untyped;
9+
10+
[JsonPropertyName("type")]
11+
public IssueType? Type { get; init; }
12+
}

src/Octokit.Webhooks/Models/Issue.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,4 +92,7 @@ public sealed record Issue
9292

9393
[JsonPropertyName("state_reason")]
9494
public string? StateReason { get; init; }
95+
96+
[JsonPropertyName("type")]
97+
public IssueType? Type { get; init; }
9598
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
namespace Octokit.Webhooks.Models;
2+
3+
[PublicAPI]
4+
public sealed record IssueType
5+
{
6+
[JsonPropertyName("id")]
7+
public long Id { get; init; }
8+
9+
[JsonPropertyName("node_id")]
10+
public string NodeId { get; init; } = null!;
11+
12+
[JsonPropertyName("name")]
13+
public string Name { get; init; } = null!;
14+
15+
[JsonPropertyName("description")]
16+
public string? Description { get; init; }
17+
18+
[JsonPropertyName("color")]
19+
public string? Color { get; init; }
20+
21+
[JsonPropertyName("created_at")]
22+
[JsonConverter(typeof(DateTimeOffsetConverter))]
23+
public DateTimeOffset CreatedAt { get; init; }
24+
25+
[JsonPropertyName("updated_at")]
26+
[JsonConverter(typeof(DateTimeOffsetConverter))]
27+
public DateTimeOffset UpdatedAt { get; init; }
28+
29+
[JsonPropertyName("is_enabled")]
30+
public bool IsEnabled { get; init; }
31+
}

src/Octokit.Webhooks/WebhookEventProcessor.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -645,10 +645,12 @@ private Task ProcessIssuesWebhookAsync(WebhookHeaders headers, IssuesEvent issue
645645
IssuesActionValue.Pinned => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Pinned),
646646
IssuesActionValue.Reopened => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Reopened),
647647
IssuesActionValue.Transferred => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Transferred),
648+
IssuesActionValue.Typed => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Typed),
648649
IssuesActionValue.Unassigned => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Unassigned),
649650
IssuesActionValue.Unlabeled => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Unlabeled),
650651
IssuesActionValue.Unlocked => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Unlocked),
651652
IssuesActionValue.Unpinned => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Unpinned),
653+
IssuesActionValue.Untyped => this.ProcessIssuesWebhookAsync(headers, issuesEvent, IssuesAction.Untyped),
652654
_ => Task.CompletedTask,
653655
};
654656

Lines changed: 234 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,234 @@
1+
{
2+
"action": "typed",
3+
"issue": {
4+
"url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1",
5+
"repository_url": "https://api.github.com/repos/Particular/SampleWebhooks",
6+
"labels_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1/labels{/name}",
7+
"comments_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1/comments",
8+
"events_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1/events",
9+
"html_url": "https://github.com/Particular/SampleWebhooks/issues/1",
10+
"id": 3138083312,
11+
"node_id": "I_kwDOO6H89867C1nw",
12+
"number": 1,
13+
"title": "Test issue",
14+
"user": {
15+
"login": "DavidBoike",
16+
"id": 427110,
17+
"node_id": "MDQ6VXNlcjQyNzExMA==",
18+
"avatar_url": "https://avatars.githubusercontent.com/u/427110?v=4",
19+
"gravatar_id": "",
20+
"url": "https://api.github.com/users/DavidBoike",
21+
"html_url": "https://github.com/DavidBoike",
22+
"followers_url": "https://api.github.com/users/DavidBoike/followers",
23+
"following_url": "https://api.github.com/users/DavidBoike/following{/other_user}",
24+
"gists_url": "https://api.github.com/users/DavidBoike/gists{/gist_id}",
25+
"starred_url": "https://api.github.com/users/DavidBoike/starred{/owner}{/repo}",
26+
"subscriptions_url": "https://api.github.com/users/DavidBoike/subscriptions",
27+
"organizations_url": "https://api.github.com/users/DavidBoike/orgs",
28+
"repos_url": "https://api.github.com/users/DavidBoike/repos",
29+
"events_url": "https://api.github.com/users/DavidBoike/events{/privacy}",
30+
"received_events_url": "https://api.github.com/users/DavidBoike/received_events",
31+
"type": "User",
32+
"user_view_type": "public",
33+
"site_admin": false
34+
},
35+
"labels": [
36+
37+
],
38+
"state": "open",
39+
"locked": false,
40+
"assignee": null,
41+
"assignees": [
42+
43+
],
44+
"milestone": null,
45+
"comments": 0,
46+
"created_at": "2025-06-11T20:53:24Z",
47+
"updated_at": "2025-06-11T20:53:29Z",
48+
"closed_at": null,
49+
"author_association": "MEMBER",
50+
"type": {
51+
"id": 401030,
52+
"node_id": "IT_kwDOAEzhac4ABh6G",
53+
"name": "Feature",
54+
"description": "A request, idea, or new functionality",
55+
"color": "blue",
56+
"created_at": "2024-01-25T09:43:49Z",
57+
"updated_at": "2024-10-08T08:42:30Z",
58+
"is_enabled": true
59+
},
60+
"active_lock_reason": null,
61+
"sub_issues_summary": {
62+
"total": 0,
63+
"completed": 0,
64+
"percent_completed": 0
65+
},
66+
"body": "This is the issue description.",
67+
"reactions": {
68+
"url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1/reactions",
69+
"total_count": 0,
70+
"+1": 0,
71+
"-1": 0,
72+
"laugh": 0,
73+
"hooray": 0,
74+
"confused": 0,
75+
"heart": 0,
76+
"rocket": 0,
77+
"eyes": 0
78+
},
79+
"timeline_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/1/timeline",
80+
"performed_via_github_app": null,
81+
"state_reason": null
82+
},
83+
"type": {
84+
"id": 401030,
85+
"node_id": "IT_kwDOAEzhac4ABh6G",
86+
"name": "Feature",
87+
"description": "A request, idea, or new functionality",
88+
"color": "blue",
89+
"created_at": "2024-01-25T09:43:49Z",
90+
"updated_at": "2024-10-08T08:42:30Z",
91+
"is_enabled": true
92+
},
93+
"repository": {
94+
"id": 1000471799,
95+
"node_id": "R_kgDOO6H89w",
96+
"name": "SampleWebhooks",
97+
"full_name": "Particular/SampleWebhooks",
98+
"private": false,
99+
"owner": {
100+
"login": "Particular",
101+
"id": 5038441,
102+
"node_id": "MDEyOk9yZ2FuaXphdGlvbjUwMzg0NDE=",
103+
"avatar_url": "https://avatars.githubusercontent.com/u/5038441?v=4",
104+
"gravatar_id": "",
105+
"url": "https://api.github.com/users/Particular",
106+
"html_url": "https://github.com/Particular",
107+
"followers_url": "https://api.github.com/users/Particular/followers",
108+
"following_url": "https://api.github.com/users/Particular/following{/other_user}",
109+
"gists_url": "https://api.github.com/users/Particular/gists{/gist_id}",
110+
"starred_url": "https://api.github.com/users/Particular/starred{/owner}{/repo}",
111+
"subscriptions_url": "https://api.github.com/users/Particular/subscriptions",
112+
"organizations_url": "https://api.github.com/users/Particular/orgs",
113+
"repos_url": "https://api.github.com/users/Particular/repos",
114+
"events_url": "https://api.github.com/users/Particular/events{/privacy}",
115+
"received_events_url": "https://api.github.com/users/Particular/received_events",
116+
"type": "Organization",
117+
"user_view_type": "public",
118+
"site_admin": false
119+
},
120+
"html_url": "https://github.com/Particular/SampleWebhooks",
121+
"description": "Using to generate GitHub webhook sample payloads",
122+
"fork": false,
123+
"url": "https://api.github.com/repos/Particular/SampleWebhooks",
124+
"forks_url": "https://api.github.com/repos/Particular/SampleWebhooks/forks",
125+
"keys_url": "https://api.github.com/repos/Particular/SampleWebhooks/keys{/key_id}",
126+
"collaborators_url": "https://api.github.com/repos/Particular/SampleWebhooks/collaborators{/collaborator}",
127+
"teams_url": "https://api.github.com/repos/Particular/SampleWebhooks/teams",
128+
"hooks_url": "https://api.github.com/repos/Particular/SampleWebhooks/hooks",
129+
"issue_events_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/events{/number}",
130+
"events_url": "https://api.github.com/repos/Particular/SampleWebhooks/events",
131+
"assignees_url": "https://api.github.com/repos/Particular/SampleWebhooks/assignees{/user}",
132+
"branches_url": "https://api.github.com/repos/Particular/SampleWebhooks/branches{/branch}",
133+
"tags_url": "https://api.github.com/repos/Particular/SampleWebhooks/tags",
134+
"blobs_url": "https://api.github.com/repos/Particular/SampleWebhooks/git/blobs{/sha}",
135+
"git_tags_url": "https://api.github.com/repos/Particular/SampleWebhooks/git/tags{/sha}",
136+
"git_refs_url": "https://api.github.com/repos/Particular/SampleWebhooks/git/refs{/sha}",
137+
"trees_url": "https://api.github.com/repos/Particular/SampleWebhooks/git/trees{/sha}",
138+
"statuses_url": "https://api.github.com/repos/Particular/SampleWebhooks/statuses/{sha}",
139+
"languages_url": "https://api.github.com/repos/Particular/SampleWebhooks/languages",
140+
"stargazers_url": "https://api.github.com/repos/Particular/SampleWebhooks/stargazers",
141+
"contributors_url": "https://api.github.com/repos/Particular/SampleWebhooks/contributors",
142+
"subscribers_url": "https://api.github.com/repos/Particular/SampleWebhooks/subscribers",
143+
"subscription_url": "https://api.github.com/repos/Particular/SampleWebhooks/subscription",
144+
"commits_url": "https://api.github.com/repos/Particular/SampleWebhooks/commits{/sha}",
145+
"git_commits_url": "https://api.github.com/repos/Particular/SampleWebhooks/git/commits{/sha}",
146+
"comments_url": "https://api.github.com/repos/Particular/SampleWebhooks/comments{/number}",
147+
"issue_comment_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues/comments{/number}",
148+
"contents_url": "https://api.github.com/repos/Particular/SampleWebhooks/contents/{+path}",
149+
"compare_url": "https://api.github.com/repos/Particular/SampleWebhooks/compare/{base}...{head}",
150+
"merges_url": "https://api.github.com/repos/Particular/SampleWebhooks/merges",
151+
"archive_url": "https://api.github.com/repos/Particular/SampleWebhooks/{archive_format}{/ref}",
152+
"downloads_url": "https://api.github.com/repos/Particular/SampleWebhooks/downloads",
153+
"issues_url": "https://api.github.com/repos/Particular/SampleWebhooks/issues{/number}",
154+
"pulls_url": "https://api.github.com/repos/Particular/SampleWebhooks/pulls{/number}",
155+
"milestones_url": "https://api.github.com/repos/Particular/SampleWebhooks/milestones{/number}",
156+
"notifications_url": "https://api.github.com/repos/Particular/SampleWebhooks/notifications{?since,all,participating}",
157+
"labels_url": "https://api.github.com/repos/Particular/SampleWebhooks/labels{/name}",
158+
"releases_url": "https://api.github.com/repos/Particular/SampleWebhooks/releases{/id}",
159+
"deployments_url": "https://api.github.com/repos/Particular/SampleWebhooks/deployments",
160+
"created_at": "2025-06-11T20:52:32Z",
161+
"updated_at": "2025-06-11T20:52:39Z",
162+
"pushed_at": "2025-06-11T20:52:32Z",
163+
"git_url": "git://github.com/Particular/SampleWebhooks.git",
164+
"ssh_url": "git@github.com:Particular/SampleWebhooks.git",
165+
"clone_url": "https://github.com/Particular/SampleWebhooks.git",
166+
"svn_url": "https://github.com/Particular/SampleWebhooks",
167+
"homepage": null,
168+
"size": 0,
169+
"stargazers_count": 0,
170+
"watchers_count": 0,
171+
"language": null,
172+
"has_issues": true,
173+
"has_projects": true,
174+
"has_downloads": true,
175+
"has_wiki": false,
176+
"has_pages": false,
177+
"has_discussions": false,
178+
"forks_count": 0,
179+
"mirror_url": null,
180+
"archived": false,
181+
"disabled": false,
182+
"open_issues_count": 1,
183+
"license": null,
184+
"allow_forking": true,
185+
"is_template": false,
186+
"web_commit_signoff_required": false,
187+
"topics": [
188+
189+
],
190+
"visibility": "public",
191+
"forks": 0,
192+
"open_issues": 1,
193+
"watchers": 0,
194+
"default_branch": "main",
195+
"custom_properties": {
196+
197+
}
198+
},
199+
"organization": {
200+
"login": "Particular",
201+
"id": 5038441,
202+
"node_id": "MDEyOk9yZ2FuaXphdGlvbjUwMzg0NDE=",
203+
"url": "https://api.github.com/orgs/Particular",
204+
"repos_url": "https://api.github.com/orgs/Particular/repos",
205+
"events_url": "https://api.github.com/orgs/Particular/events",
206+
"hooks_url": "https://api.github.com/orgs/Particular/hooks",
207+
"issues_url": "https://api.github.com/orgs/Particular/issues",
208+
"members_url": "https://api.github.com/orgs/Particular/members{/member}",
209+
"public_members_url": "https://api.github.com/orgs/Particular/public_members{/member}",
210+
"avatar_url": "https://avatars.githubusercontent.com/u/5038441?v=4",
211+
"description": ""
212+
},
213+
"sender": {
214+
"login": "DavidBoike",
215+
"id": 427110,
216+
"node_id": "MDQ6VXNlcjQyNzExMA==",
217+
"avatar_url": "https://avatars.githubusercontent.com/u/427110?v=4",
218+
"gravatar_id": "",
219+
"url": "https://api.github.com/users/DavidBoike",
220+
"html_url": "https://github.com/DavidBoike",
221+
"followers_url": "https://api.github.com/users/DavidBoike/followers",
222+
"following_url": "https://api.github.com/users/DavidBoike/following{/other_user}",
223+
"gists_url": "https://api.github.com/users/DavidBoike/gists{/gist_id}",
224+
"starred_url": "https://api.github.com/users/DavidBoike/starred{/owner}{/repo}",
225+
"subscriptions_url": "https://api.github.com/users/DavidBoike/subscriptions",
226+
"organizations_url": "https://api.github.com/users/DavidBoike/orgs",
227+
"repos_url": "https://api.github.com/users/DavidBoike/repos",
228+
"events_url": "https://api.github.com/users/DavidBoike/events{/privacy}",
229+
"received_events_url": "https://api.github.com/users/DavidBoike/received_events",
230+
"type": "User",
231+
"user_view_type": "public",
232+
"site_admin": false
233+
}
234+
}

0 commit comments

Comments
 (0)