...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package gitlab
18
19 import (
20 "encoding/json"
21 "fmt"
22 "net/http"
23 )
24
25
26 type EventType string
27
28
29 const (
30 EventConfidentialIssue EventType = "Confidential Issue Hook"
31 EventConfidentialNote EventType = "Confidential Note Hook"
32 EventTypeBuild EventType = "Build Hook"
33 EventTypeDeployment EventType = "Deployment Hook"
34 EventTypeFeatureFlag EventType = "Feature Flag Hook"
35 EventTypeIssue EventType = "Issue Hook"
36 EventTypeJob EventType = "Job Hook"
37 EventTypeMember EventType = "Member Hook"
38 EventTypeMergeRequest EventType = "Merge Request Hook"
39 EventTypeNote EventType = "Note Hook"
40 EventTypePipeline EventType = "Pipeline Hook"
41 EventTypePush EventType = "Push Hook"
42 EventTypeRelease EventType = "Release Hook"
43 EventTypeServiceHook EventType = "Service Hook"
44 EventTypeSubGroup EventType = "Subgroup Hook"
45 EventTypeSystemHook EventType = "System Hook"
46 EventTypeTagPush EventType = "Tag Push Hook"
47 EventTypeWikiPage EventType = "Wiki Page Hook"
48 )
49
50 const (
51 eventObjectKindPush = "push"
52 eventObjectKindTagPush = "tag_push"
53 eventObjectKindMergeRequest = "merge_request"
54 )
55
56 const (
57 noteableTypeCommit = "Commit"
58 noteableTypeIssue = "Issue"
59 noteableTypeMergeRequest = "MergeRequest"
60 noteableTypeSnippet = "Snippet"
61 )
62
63 type noteEvent struct {
64 ObjectKind string `json:"object_kind"`
65 ObjectAttributes struct {
66 NoteableType string `json:"noteable_type"`
67 } `json:"object_attributes"`
68 }
69
70 type serviceEvent struct {
71 ObjectKind string `json:"object_kind"`
72 }
73
74 const eventTypeHeader = "X-Gitlab-Event"
75
76
77 func HookEventType(r *http.Request) EventType {
78 return EventType(r.Header.Get(eventTypeHeader))
79 }
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98 func ParseHook(eventType EventType, payload []byte) (event interface{}, err error) {
99 switch eventType {
100 case EventTypeSystemHook:
101 return ParseSystemhook(payload)
102 default:
103 return ParseWebhook(eventType, payload)
104 }
105 }
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126 func ParseSystemhook(payload []byte) (event interface{}, err error) {
127 e := &systemHookEvent{}
128 err = json.Unmarshal(payload, e)
129 if err != nil {
130 return nil, err
131 }
132
133 switch e.EventName {
134 case eventObjectKindPush:
135 event = &PushSystemEvent{}
136 case eventObjectKindTagPush:
137 event = &TagPushSystemEvent{}
138 case "repository_update":
139 event = &RepositoryUpdateSystemEvent{}
140 case
141 "project_create",
142 "project_update",
143 "project_destroy",
144 "project_transfer",
145 "project_rename":
146 event = &ProjectSystemEvent{}
147 case
148 "group_create",
149 "group_destroy",
150 "group_rename":
151 event = &GroupSystemEvent{}
152 case "key_create", "key_destroy":
153 event = &KeySystemEvent{}
154 case
155 "user_create",
156 "user_destroy",
157 "user_rename",
158 "user_failed_login":
159 event = &UserSystemEvent{}
160 case
161 "user_add_to_group",
162 "user_remove_from_group",
163 "user_update_for_group":
164 event = &UserGroupSystemEvent{}
165 case
166 "user_add_to_team",
167 "user_remove_from_team",
168 "user_update_for_team":
169 event = &UserTeamSystemEvent{}
170 default:
171 switch e.ObjectKind {
172 case string(MergeRequestEventTargetType):
173 event = &MergeEvent{}
174 default:
175 return nil, fmt.Errorf("unexpected system hook type %s", e.EventName)
176 }
177 }
178
179 if err := json.Unmarshal(payload, event); err != nil {
180 return nil, err
181 }
182
183 return event, nil
184 }
185
186
187 func WebhookEventType(r *http.Request) EventType {
188 return EventType(r.Header.Get(eventTypeHeader))
189 }
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210 func ParseWebhook(eventType EventType, payload []byte) (event interface{}, err error) {
211 switch eventType {
212 case EventTypeBuild:
213 event = &BuildEvent{}
214 case EventTypeDeployment:
215 event = &DeploymentEvent{}
216 case EventTypeFeatureFlag:
217 event = &FeatureFlagEvent{}
218 case EventTypeIssue, EventConfidentialIssue:
219 event = &IssueEvent{}
220 case EventTypeJob:
221 event = &JobEvent{}
222 case EventTypeMember:
223 event = &MemberEvent{}
224 case EventTypeMergeRequest:
225 event = &MergeEvent{}
226 case EventTypeNote, EventConfidentialNote:
227 note := ¬eEvent{}
228 err := json.Unmarshal(payload, note)
229 if err != nil {
230 return nil, err
231 }
232
233 if note.ObjectKind != string(NoteEventTargetType) {
234 return nil, fmt.Errorf("unexpected object kind %s", note.ObjectKind)
235 }
236
237 switch note.ObjectAttributes.NoteableType {
238 case noteableTypeCommit:
239 event = &CommitCommentEvent{}
240 case noteableTypeMergeRequest:
241 event = &MergeCommentEvent{}
242 case noteableTypeIssue:
243 event = &IssueCommentEvent{}
244 case noteableTypeSnippet:
245 event = &SnippetCommentEvent{}
246 default:
247 return nil, fmt.Errorf("unexpected noteable type %s", note.ObjectAttributes.NoteableType)
248 }
249 case EventTypePipeline:
250 event = &PipelineEvent{}
251 case EventTypePush:
252 event = &PushEvent{}
253 case EventTypeRelease:
254 event = &ReleaseEvent{}
255 case EventTypeServiceHook:
256 service := &serviceEvent{}
257 err := json.Unmarshal(payload, service)
258 if err != nil {
259 return nil, err
260 }
261 switch service.ObjectKind {
262 case eventObjectKindPush:
263 event = &PushEvent{}
264 case eventObjectKindTagPush:
265 event = &TagEvent{}
266 case eventObjectKindMergeRequest:
267 event = &MergeEvent{}
268 default:
269 return nil, fmt.Errorf("unexpected service type %s", service.ObjectKind)
270 }
271 case EventTypeSubGroup:
272 event = &SubGroupEvent{}
273 case EventTypeTagPush:
274 event = &TagEvent{}
275 case EventTypeWikiPage:
276 event = &WikiPageEvent{}
277 default:
278 return nil, fmt.Errorf("unexpected event type: %s", eventType)
279 }
280
281 if err := json.Unmarshal(payload, event); err != nil {
282 return nil, err
283 }
284
285 return event, nil
286 }
287
View as plain text