Skip to content
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

Add more webhooks support and refactor webhook templates directory #3929

Merged
merged 12 commits into from
May 16, 2018
2 changes: 1 addition & 1 deletion docs/content/doc/features/comparison.en-us.md
Original file line number Diff line number Diff line change
Expand Up @@ -537,7 +537,7 @@ _Symbols used in table:_
</tr>
<tr>
<td>Webhook support</td>
<td></td>
<td></td>
<td>✓</td>
<td>✓</td>
<td>✓</td>
Expand Down
20 changes: 20 additions & 0 deletions models/action.go
Original file line number Diff line number Diff line change
Expand Up @@ -618,6 +618,16 @@ func CommitRepoAction(opts CommitRepoActionOptions) error {
case ActionDeleteBranch: // Delete Branch
isHookEventPush = true

if err = PrepareWebhooks(repo, HookEventDelete, &api.DeletePayload{
Ref: refName,
RefType: "branch",
PusherType: api.PusherTypeUser,
Repo: apiRepo,
Sender: apiPusher,
}); err != nil {
return fmt.Errorf("PrepareWebhooks.(delete branch): %v", err)
}

case ActionPushTag: // Create
isHookEventPush = true

Expand All @@ -640,6 +650,16 @@ func CommitRepoAction(opts CommitRepoActionOptions) error {
}
case ActionDeleteTag: // Delete Tag
isHookEventPush = true

if err = PrepareWebhooks(repo, HookEventDelete, &api.DeletePayload{
Ref: refName,
RefType: "tag",
PusherType: api.PusherTypeUser,
Repo: apiRepo,
Sender: apiPusher,
}); err != nil {
return fmt.Errorf("PrepareWebhooks.(delete tag): %v", err)
}
}

if isHookEventPush {
Expand Down
110 changes: 92 additions & 18 deletions models/issue_comment.go
Original file line number Diff line number Diff line change
Expand Up @@ -83,9 +83,10 @@ const (
type Comment struct {
ID int64 `xorm:"pk autoincr"`
Type CommentType
PosterID int64 `xorm:"INDEX"`
Poster *User `xorm:"-"`
IssueID int64 `xorm:"INDEX"`
PosterID int64 `xorm:"INDEX"`
Poster *User `xorm:"-"`
IssueID int64 `xorm:"INDEX"`
Issue *Issue `xorm:"-"`
LabelID int64
Label *Label `xorm:"-"`
OldMilestoneID int64
Expand Down Expand Up @@ -116,6 +117,15 @@ type Comment struct {
ShowTag CommentTag `xorm:"-"`
}

// LoadIssue loads issue from database
func (c *Comment) LoadIssue() (err error) {
if c.Issue != nil {
return nil
}
c.Issue, err = GetIssueByID(c.IssueID)
return
}

// AfterLoad is invoked from XORM after setting the values of all fields of this object.
func (c *Comment) AfterLoad(session *xorm.Session) {
var err error
Expand Down Expand Up @@ -146,40 +156,40 @@ func (c *Comment) AfterDelete() {

// HTMLURL formats a URL-string to the issue-comment
func (c *Comment) HTMLURL() string {
issue, err := GetIssueByID(c.IssueID)
err := c.LoadIssue()
if err != nil { // Silently dropping errors :unamused:
log.Error(4, "GetIssueByID(%d): %v", c.IssueID, err)
log.Error(4, "LoadIssue(%d): %v", c.IssueID, err)
return ""
}
return fmt.Sprintf("%s#%s", issue.HTMLURL(), c.HashTag())
return fmt.Sprintf("%s#%s", c.Issue.HTMLURL(), c.HashTag())
}

// IssueURL formats a URL-string to the issue
func (c *Comment) IssueURL() string {
issue, err := GetIssueByID(c.IssueID)
err := c.LoadIssue()
if err != nil { // Silently dropping errors :unamused:
log.Error(4, "GetIssueByID(%d): %v", c.IssueID, err)
log.Error(4, "LoadIssue(%d): %v", c.IssueID, err)
return ""
}

if issue.IsPull {
if c.Issue.IsPull {
return ""
}
return issue.HTMLURL()
return c.Issue.HTMLURL()
}

// PRURL formats a URL-string to the pull-request
func (c *Comment) PRURL() string {
issue, err := GetIssueByID(c.IssueID)
err := c.LoadIssue()
if err != nil { // Silently dropping errors :unamused:
log.Error(4, "GetIssueByID(%d): %v", c.IssueID, err)
log.Error(4, "LoadIssue(%d): %v", c.IssueID, err)
return ""
}

if !issue.IsPull {
if !c.Issue.IsPull {
return ""
}
return issue.HTMLURL()
return c.Issue.HTMLURL()
}

// APIFormat converts a Comment to the api.Comment format
Expand All @@ -196,9 +206,14 @@ func (c *Comment) APIFormat() *api.Comment {
}
}

// CommentHashTag returns unique hash tag for comment id.
func CommentHashTag(id int64) string {
return fmt.Sprintf("issuecomment-%d", id)
}

// HashTag returns unique hash tag for comment.
func (c *Comment) HashTag() string {
return "issuecomment-" + com.ToStr(c.ID)
return CommentHashTag(c.ID)
}

// EventTag returns unique event hash tag for comment.
Expand Down Expand Up @@ -576,14 +591,29 @@ func CreateComment(opts *CreateCommentOptions) (comment *Comment, err error) {

// CreateIssueComment creates a plain issue comment.
func CreateIssueComment(doer *User, repo *Repository, issue *Issue, content string, attachments []string) (*Comment, error) {
return CreateComment(&CreateCommentOptions{
comment, err := CreateComment(&CreateCommentOptions{
Type: CommentTypeComment,
Doer: doer,
Repo: repo,
Issue: issue,
Content: content,
Attachments: attachments,
})
if err != nil {
return nil, fmt.Errorf("CreateComment: %v", err)
}

mode, _ := AccessLevel(doer.ID, repo)
if err = PrepareWebhooks(repo, HookEventIssueComment, &api.IssueCommentPayload{
Action: api.HookIssueCommentCreated,
Issue: issue.APIFormat(),
Comment: comment.APIFormat(),
Repository: repo.APIFormat(mode),
Sender: doer.APIFormat(),
}); err != nil {
log.Error(2, "PrepareWebhooks [comment_id: %d]: %v", comment.ID, err)
}
return comment, nil
}

// CreateRefComment creates a commit reference comment to issue.
Expand Down Expand Up @@ -696,17 +726,41 @@ func GetCommentsByRepoIDSince(repoID, since int64) ([]*Comment, error) {
}

// UpdateComment updates information of comment.
func UpdateComment(c *Comment) error {
func UpdateComment(doer *User, c *Comment, oldContent string) error {
if _, err := x.ID(c.ID).AllCols().Update(c); err != nil {
return err
} else if c.Type == CommentTypeComment {
UpdateIssueIndexer(c.IssueID)
}

if err := c.LoadIssue(); err != nil {
return err
}
if err := c.Issue.LoadAttributes(); err != nil {
return err
}

mode, _ := AccessLevel(doer.ID, c.Issue.Repo)
if err := PrepareWebhooks(c.Issue.Repo, HookEventIssueComment, &api.IssueCommentPayload{
Action: api.HookIssueCommentEdited,
Issue: c.Issue.APIFormat(),
Comment: c.APIFormat(),
Changes: &api.ChangesPayload{
Body: &api.ChangesFromPayload{
From: oldContent,
},
},
Repository: c.Issue.Repo.APIFormat(mode),
Sender: doer.APIFormat(),
}); err != nil {
log.Error(2, "PrepareWebhooks [comment_id: %d]: %v", c.ID, err)
}

return nil
}

// DeleteComment deletes the comment
func DeleteComment(comment *Comment) error {
func DeleteComment(doer *User, comment *Comment) error {
sess := x.NewSession()
defer sess.Close()
if err := sess.Begin(); err != nil {
Expand All @@ -733,5 +787,25 @@ func DeleteComment(comment *Comment) error {
} else if comment.Type == CommentTypeComment {
UpdateIssueIndexer(comment.IssueID)
}

if err := comment.LoadIssue(); err != nil {
return err
}
if err := comment.Issue.LoadAttributes(); err != nil {
return err
}

mode, _ := AccessLevel(doer.ID, comment.Issue.Repo)

if err := PrepareWebhooks(comment.Issue.Repo, HookEventIssueComment, &api.IssueCommentPayload{
Action: api.HookIssueCommentDeleted,
Issue: comment.Issue.APIFormat(),
Comment: comment.APIFormat(),
Repository: comment.Issue.Repo.APIFormat(mode),
Sender: doer.APIFormat(),
}); err != nil {
log.Error(2, "PrepareWebhooks [comment_id: %d]: %v", comment.ID, err)
}

return nil
}
47 changes: 46 additions & 1 deletion models/issue_milestone.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,9 @@
package models

import (
"fmt"

"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/util"
api "code.gitea.io/sdk/gitea"
Expand Down Expand Up @@ -358,7 +361,49 @@ func ChangeMilestoneAssign(issue *Issue, doer *User, oldMilestoneID int64) (err
if err = changeMilestoneAssign(sess, doer, issue, oldMilestoneID); err != nil {
return err
}
return sess.Commit()

if err = sess.Commit(); err != nil {
return fmt.Errorf("Commit: %v", err)
}

var hookAction api.HookIssueAction
if issue.MilestoneID > 0 {
hookAction = api.HookIssueMilestoned
} else {
hookAction = api.HookIssueDemilestoned
}

if err = issue.LoadAttributes(); err != nil {
return err
}

mode, _ := AccessLevel(doer.ID, issue.Repo)
if issue.IsPull {
err = issue.PullRequest.LoadIssue()
if err != nil {
log.Error(2, "LoadIssue: %v", err)
return
}
err = PrepareWebhooks(issue.Repo, HookEventPullRequest, &api.PullRequestPayload{
Action: hookAction,
Index: issue.Index,
PullRequest: issue.PullRequest.APIFormat(),
Repository: issue.Repo.APIFormat(mode),
Sender: doer.APIFormat(),
})
} else {
err = PrepareWebhooks(issue.Repo, HookEventIssues, &api.IssuePayload{
Action: hookAction,
Index: issue.Index,
Issue: issue.APIFormat(),
Repository: issue.Repo.APIFormat(mode),
Sender: doer.APIFormat(),
})
}
if err != nil {
log.Error(2, "PrepareWebhooks [is_pull: %v]: %v", issue.IsPull, err)
}
return nil
}

// DeleteMilestoneByRepoID deletes a milestone from a repository.
Expand Down
2 changes: 2 additions & 0 deletions models/issue_milestone_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,8 @@ func TestChangeMilestoneAssign(t *testing.T) {
assert.NoError(t, PrepareTestDatabase())
issue := AssertExistsAndLoadBean(t, &Issue{RepoID: 1}).(*Issue)
doer := AssertExistsAndLoadBean(t, &User{ID: 2}).(*User)
assert.NotNil(t, issue)
assert.NotNil(t, doer)

oldMilestoneID := issue.MilestoneID
issue.MilestoneID = 2
Expand Down
22 changes: 21 additions & 1 deletion models/release.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import (
"strings"

"code.gitea.io/git"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/process"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/util"
Expand Down Expand Up @@ -190,8 +191,27 @@ func CreateRelease(gitRepo *git.Repository, rel *Release, attachmentUUIDs []stri
}

err = addReleaseAttachments(rel.ID, attachmentUUIDs)
if err != nil {
return err
}

return err
if !rel.IsDraft {
if err := rel.LoadAttributes(); err != nil {
log.Error(2, "LoadAttributes: %v", err)
} else {
mode, _ := AccessLevel(rel.PublisherID, rel.Repo)
if err := PrepareWebhooks(rel.Repo, HookEventRelease, &api.ReleasePayload{
Action: api.HookReleasePublished,
Release: rel.APIFormat(),
Repository: rel.Repo.APIFormat(mode),
Sender: rel.Publisher.APIFormat(),
}); err != nil {
log.Error(2, "PrepareWebhooks: %v", err)
}
}
}

return nil
}

// GetRelease returns release by given ID.
Expand Down
11 changes: 11 additions & 0 deletions models/repo.go
Original file line number Diff line number Diff line change
Expand Up @@ -2456,6 +2456,17 @@ func ForkRepository(doer, u *User, oldRepo *Repository, name, desc string) (_ *R
return nil, err
}

oldMode, _ := AccessLevel(doer.ID, oldRepo)
mode, _ := AccessLevel(doer.ID, repo)

if err = PrepareWebhooks(oldRepo, HookEventFork, &api.ForkPayload{
Forkee: repo.APIFormat(mode),
Repo: oldRepo.APIFormat(oldMode),
Sender: doer.APIFormat(),
}); err != nil {
log.Error(2, "PrepareWebhooks [repo_id: %d]: %v", oldRepo.ID, err)
}

if err = repo.UpdateSize(); err != nil {
log.Error(4, "Failed to update size for repository: %v", err)
}
Expand Down
Loading