-
-
Notifications
You must be signed in to change notification settings - Fork 5.8k
Let API create and edit system webhooks #26418
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -1520,7 +1520,7 @@ func Routes() *web.Route { | |
m.Post("/{username}/{reponame}", admin.AdoptRepository) | ||
m.Delete("/{username}/{reponame}", admin.DeleteUnadoptedRepository) | ||
}) | ||
m.Group("/hooks", func() { | ||
m.Group("/hooks/{configType:system|default}", func() { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is the core change. Almost everything else is fall-out from making this one line change. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. In #23142 (comment), lunny suggested what I added as Respectfully, I think we must not. The old behaviour was inconsistent:
For "backwards compatibility", we could chose to keep the The confused behaviour was in the original version of |
||
m.Combo("").Get(admin.ListHooks). | ||
Post(bind(api.CreateHookOption{}), admin.CreateHook) | ||
m.Combo("/{id}").Get(admin.GetHook). | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -4,6 +4,7 @@ | |
package utils | ||
|
||
import ( | ||
"errors" | ||
"fmt" | ||
"net/http" | ||
"strings" | ||
|
@@ -100,9 +101,9 @@ func checkCreateHookOption(ctx *context.APIContext, form *api.CreateHookOption) | |
return true | ||
} | ||
|
||
// AddSystemHook add a system hook | ||
func AddSystemHook(ctx *context.APIContext, form *api.CreateHookOption) { | ||
hook, ok := addHook(ctx, form, 0, 0) | ||
// add a system or default hook | ||
func AddAdminHook(ctx *context.APIContext, form *api.CreateHookOption, isSystemWebhook bool) { | ||
hook, ok := addHook(ctx, form, 0, 0, isSystemWebhook) | ||
if ok { | ||
h, err := webhook_service.ToHook(setting.AppSubURL+"/admin", hook) | ||
if err != nil { | ||
|
@@ -115,7 +116,7 @@ func AddSystemHook(ctx *context.APIContext, form *api.CreateHookOption) { | |
|
||
// AddOwnerHook adds a hook to an user or organization | ||
func AddOwnerHook(ctx *context.APIContext, owner *user_model.User, form *api.CreateHookOption) { | ||
hook, ok := addHook(ctx, form, owner.ID, 0) | ||
hook, ok := addHook(ctx, form, owner.ID, 0, false) | ||
if !ok { | ||
return | ||
} | ||
|
@@ -129,7 +130,7 @@ func AddOwnerHook(ctx *context.APIContext, owner *user_model.User, form *api.Cre | |
// AddRepoHook add a hook to a repo. Writes to `ctx` accordingly | ||
func AddRepoHook(ctx *context.APIContext, form *api.CreateHookOption) { | ||
repo := ctx.Repo | ||
hook, ok := addHook(ctx, form, 0, repo.Repository.ID) | ||
hook, ok := addHook(ctx, form, 0, repo.Repository.ID, false) | ||
if !ok { | ||
return | ||
} | ||
|
@@ -159,9 +160,18 @@ func pullHook(events []string, event string) bool { | |
return util.SliceContainsString(events, event, true) || util.SliceContainsString(events, string(webhook_module.HookEventPullRequest), true) | ||
} | ||
|
||
// addHook add the hook specified by `form`, `ownerID` and `repoID`. If there is | ||
// an error, write to `ctx` accordingly. Return (webhook, ok) | ||
func addHook(ctx *context.APIContext, form *api.CreateHookOption, ownerID, repoID int64) (*webhook.Webhook, bool) { | ||
// addHook add the hook specified by `form`, `ownerID`, `repoID`, and `isSystemWebhook`. | ||
// `isSystemWebhook` == true means it's a hook attached automatically to all repos | ||
// `isSystemWebhook` == false && ownerID == 0 && repoID == 0 means it's a default hook, automatically copied to all new repos | ||
// `ownerID` != 0 means it runs on all their repos | ||
// `repoID` != 0 means it is an active hook, attached to that repo | ||
// If there is an error, write to `ctx` accordingly. Return (webhook, ok) | ||
func addHook(ctx *context.APIContext, form *api.CreateHookOption, ownerID, repoID int64, isSystemWebhook bool) (*webhook.Webhook, bool) { | ||
if isSystemWebhook && (ownerID != 0 || repoID != 0) { | ||
ctx.Error(http.StatusInternalServerError, "addHook", fmt.Errorf("cannot create a hook with an owner or repo that is also a system hook")) | ||
return nil, false | ||
} | ||
|
||
if !checkCreateHookOption(ctx, form) { | ||
return nil, false | ||
} | ||
|
@@ -170,12 +180,13 @@ func addHook(ctx *context.APIContext, form *api.CreateHookOption, ownerID, repoI | |
form.Events = []string{"push"} | ||
} | ||
w := &webhook.Webhook{ | ||
OwnerID: ownerID, | ||
RepoID: repoID, | ||
URL: form.Config["url"], | ||
ContentType: webhook.ToHookContentType(form.Config["content_type"]), | ||
Secret: form.Config["secret"], | ||
HTTPMethod: "POST", | ||
OwnerID: ownerID, | ||
RepoID: repoID, | ||
URL: form.Config["url"], | ||
ContentType: webhook.ToHookContentType(form.Config["content_type"]), | ||
Secret: form.Config["secret"], | ||
IsSystemWebhook: isSystemWebhook, | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This line is what communicates the one line change above into the backend. |
||
HTTPMethod: "POST", | ||
HookEvent: &webhook_module.HookEvent{ | ||
ChooseEvents: true, | ||
HookEvents: webhook_module.HookEvents{ | ||
|
@@ -246,22 +257,28 @@ func addHook(ctx *context.APIContext, form *api.CreateHookOption, ownerID, repoI | |
return w, true | ||
} | ||
|
||
// EditSystemHook edit system webhook `w` according to `form`. Writes to `ctx` accordingly | ||
func EditSystemHook(ctx *context.APIContext, form *api.EditHookOption, hookID int64) { | ||
hook, err := webhook.GetSystemOrDefaultWebhook(ctx, hookID) | ||
// EditAdminHook edits system/default webhook `w` according to `form`. Writes to `ctx` accordingly. | ||
func EditAdminHook(ctx *context.APIContext, form *api.EditHookOption, hookID int64, isSystemWebhook bool) { | ||
hook, err := webhook.GetAdminWebhook(ctx, hookID, isSystemWebhook) | ||
if err != nil { | ||
ctx.Error(http.StatusInternalServerError, "GetSystemOrDefaultWebhook", err) | ||
if errors.Is(err, util.ErrNotExist) { | ||
ctx.NotFound() | ||
Comment on lines
+264
to
+265
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is what adds the correct 404 to the PATCH method. |
||
} else { | ||
ctx.Error(http.StatusInternalServerError, "GetAdminWebhook", err) | ||
} | ||
return | ||
} | ||
|
||
if !editHook(ctx, form, hook) { | ||
ctx.Error(http.StatusInternalServerError, "editHook", err) | ||
return | ||
} | ||
updated, err := webhook.GetSystemOrDefaultWebhook(ctx, hookID) | ||
|
||
updated, err := webhook.GetAdminWebhook(ctx, hookID, isSystemWebhook) | ||
if err != nil { | ||
ctx.Error(http.StatusInternalServerError, "GetSystemOrDefaultWebhook", err) | ||
ctx.Error(http.StatusInternalServerError, "GetAdminWebhook", err) | ||
return | ||
} | ||
|
||
h, err := webhook_service.ToHook(setting.AppURL+"/admin", updated) | ||
if err != nil { | ||
ctx.Error(http.StatusInternalServerError, "convert.ToHook", err) | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is a break change and with no deprecated mark?