@@ -154,3 +154,184 @@ func TestDetectMatched(t *testing.T) {
154
154
})
155
155
}
156
156
}
157
+
158
+ func TestMatchIssuesEvent (t * testing.T ) {
159
+ testCases := []struct {
160
+ desc string
161
+ payload * api.IssuePayload
162
+ yamlOn string
163
+ expected bool
164
+ eventType string
165
+ }{
166
+ {
167
+ desc : "Label deletion should trigger unlabeled event" ,
168
+ payload : & api.IssuePayload {
169
+ Action : api .HookIssueLabelUpdated ,
170
+ Issue : & api.Issue {
171
+ Labels : []* api.Label {},
172
+ },
173
+ Changes : & api.ChangesPayload {
174
+ RemovedLabels : []* api.Label {
175
+ {ID : 123 , Name : "deleted-label" },
176
+ },
177
+ },
178
+ },
179
+ yamlOn : "on:\n issues:\n types: [unlabeled]" ,
180
+ expected : true ,
181
+ eventType : "unlabeled" ,
182
+ },
183
+ {
184
+ desc : "Label deletion with existing labels should trigger unlabeled event" ,
185
+ payload : & api.IssuePayload {
186
+ Action : api .HookIssueLabelUpdated ,
187
+ Issue : & api.Issue {
188
+ Labels : []* api.Label {
189
+ {ID : 456 , Name : "existing-label" },
190
+ },
191
+ },
192
+ Changes : & api.ChangesPayload {
193
+ AddedLabels : nil ,
194
+ RemovedLabels : []* api.Label {
195
+ {ID : 123 , Name : "deleted-label" },
196
+ },
197
+ },
198
+ },
199
+ yamlOn : "on:\n issues:\n types: [unlabeled]" ,
200
+ expected : true ,
201
+ eventType : "unlabeled" ,
202
+ },
203
+ {
204
+ desc : "Label addition should trigger labeled event" ,
205
+ payload : & api.IssuePayload {
206
+ Action : api .HookIssueLabelUpdated ,
207
+ Issue : & api.Issue {
208
+ Labels : []* api.Label {
209
+ {ID : 123 , Name : "new-label" },
210
+ },
211
+ },
212
+ Changes : & api.ChangesPayload {
213
+ AddedLabels : []* api.Label {
214
+ {ID : 123 , Name : "new-label" },
215
+ },
216
+ RemovedLabels : []* api.Label {}, // Empty array, no labels removed
217
+ },
218
+ },
219
+ yamlOn : "on:\n issues:\n types: [labeled]" ,
220
+ expected : true ,
221
+ eventType : "labeled" ,
222
+ },
223
+ {
224
+ desc : "Label clear should trigger unlabeled event" ,
225
+ payload : & api.IssuePayload {
226
+ Action : api .HookIssueLabelCleared ,
227
+ Issue : & api.Issue {
228
+ Labels : []* api.Label {},
229
+ },
230
+ },
231
+ yamlOn : "on:\n issues:\n types: [unlabeled]" ,
232
+ expected : true ,
233
+ eventType : "unlabeled" ,
234
+ },
235
+ {
236
+ desc : "Both adding and removing labels should trigger labeled event" ,
237
+ payload : & api.IssuePayload {
238
+ Action : api .HookIssueLabelUpdated ,
239
+ Issue : & api.Issue {
240
+ Labels : []* api.Label {
241
+ {ID : 789 , Name : "new-label" },
242
+ },
243
+ },
244
+ Changes : & api.ChangesPayload {
245
+ AddedLabels : []* api.Label {
246
+ {ID : 789 , Name : "new-label" },
247
+ },
248
+ RemovedLabels : []* api.Label {
249
+ {ID : 123 , Name : "deleted-label" },
250
+ },
251
+ },
252
+ },
253
+ yamlOn : "on:\n issues:\n types: [labeled]" ,
254
+ expected : true ,
255
+ eventType : "labeled" ,
256
+ },
257
+ {
258
+ desc : "Both adding and removing labels should trigger unlabeled event" ,
259
+ payload : & api.IssuePayload {
260
+ Action : api .HookIssueLabelUpdated ,
261
+ Issue : & api.Issue {
262
+ Labels : []* api.Label {
263
+ {ID : 789 , Name : "new-label" },
264
+ },
265
+ },
266
+ Changes : & api.ChangesPayload {
267
+ AddedLabels : []* api.Label {
268
+ {ID : 789 , Name : "new-label" },
269
+ },
270
+ RemovedLabels : []* api.Label {
271
+ {ID : 123 , Name : "deleted-label" },
272
+ },
273
+ },
274
+ },
275
+ yamlOn : "on:\n issues:\n types: [unlabeled]" ,
276
+ expected : true ,
277
+ eventType : "unlabeled" ,
278
+ },
279
+ {
280
+ desc : "Both adding and removing labels should trigger both events" ,
281
+ payload : & api.IssuePayload {
282
+ Action : api .HookIssueLabelUpdated ,
283
+ Issue : & api.Issue {
284
+ Labels : []* api.Label {
285
+ {ID : 789 , Name : "new-label" },
286
+ },
287
+ },
288
+ Changes : & api.ChangesPayload {
289
+ AddedLabels : []* api.Label {
290
+ {ID : 789 , Name : "new-label" },
291
+ },
292
+ RemovedLabels : []* api.Label {
293
+ {ID : 123 , Name : "deleted-label" },
294
+ },
295
+ },
296
+ },
297
+ yamlOn : "on:\n issues:\n types: [labeled, unlabeled]" ,
298
+ expected : true ,
299
+ eventType : "multiple" ,
300
+ },
301
+ }
302
+
303
+ for _ , tc := range testCases {
304
+ t .Run (tc .desc , func (t * testing.T ) {
305
+ evts , err := GetEventsFromContent ([]byte (tc .yamlOn ))
306
+ assert .NoError (t , err )
307
+ assert .Len (t , evts , 1 )
308
+
309
+ // Test if the event matches as expected
310
+ assert .Equal (t , tc .expected , matchIssuesEvent (tc .payload , evts [0 ]))
311
+
312
+ // For extra validation, check that action mapping works correctly
313
+ if tc .eventType == "multiple" {
314
+ // Skip direct action mapping validation for multiple events case
315
+ // as one action can map to multiple event types
316
+ return
317
+ }
318
+
319
+ // Determine expected action for single event case
320
+ var expectedAction string
321
+ switch tc .payload .Action {
322
+ case api .HookIssueLabelUpdated :
323
+ if tc .eventType == "labeled" {
324
+ expectedAction = "labeled"
325
+ } else if tc .eventType == "unlabeled" {
326
+ expectedAction = "unlabeled"
327
+ }
328
+ case api .HookIssueLabelCleared :
329
+ expectedAction = "unlabeled"
330
+ default :
331
+ expectedAction = string (tc .payload .Action )
332
+ }
333
+
334
+ assert .Equal (t , expectedAction , tc .eventType , "Event type should match expected" )
335
+ })
336
+ }
337
+ }
0 commit comments