woodpecker/server/handler/hook.go

105 lines
2.6 KiB
Go
Raw Normal View History

2014-06-04 21:25:38 +00:00
package handler
import (
"net/http"
"github.com/drone/drone/server/queue"
2014-06-04 21:25:38 +00:00
"github.com/drone/drone/server/resource/commit"
"github.com/drone/drone/server/resource/config"
"github.com/drone/drone/server/resource/repo"
"github.com/drone/drone/server/resource/user"
"github.com/gorilla/pat"
)
type HookHandler struct {
users user.UserManager
repos repo.RepoManager
commits commit.CommitManager
queue *queue.Queue
2014-06-04 21:25:38 +00:00
conf *config.Config
}
func NewHookHandler(users user.UserManager, repos repo.RepoManager, commits commit.CommitManager, conf *config.Config, queue *queue.Queue) *HookHandler {
return &HookHandler{users, repos, commits, queue, conf}
2014-06-04 21:25:38 +00:00
}
// PostHook receives a post-commit hook from GitHub, Bitbucket, etc
// GET /hook/:host
func (h *HookHandler) PostHook(w http.ResponseWriter, r *http.Request) error {
host := r.FormValue(":host")
// get the remote system's client.
remote := h.conf.GetRemote(host)
if remote == nil {
return notFound{}
}
// parse the hook payload
hook, err := remote.GetHook(r)
if err != nil {
return badRequest{err}
}
// in some cases we have neither a hook nor error. An example
// would be GitHub sending a ping request to the URL, in which
// case we'll just exit quiely with an 'OK'
if hook == nil {
w.WriteHeader(http.StatusOK)
return nil
}
2014-06-12 19:44:19 +00:00
//fmt.Printf("%#v", hook)
2014-06-04 21:25:38 +00:00
// fetch the repository from the database
repo, err := h.repos.FindName(remote.GetHost(), hook.Owner, hook.Repo)
2014-06-04 21:25:38 +00:00
if err != nil {
return notFound{}
}
if repo.Active == false ||
(repo.PostCommit == false && len(hook.PullRequest) == 0) ||
(repo.PullRequest == false && len(hook.PullRequest) != 0) {
w.WriteHeader(http.StatusOK)
return nil
}
// fetch the user from the database that owns this repo
user, err := h.users.Find(repo.UserID)
if err != nil {
return notFound{}
}
// featch the .drone.yml file from the database
client := remote.GetClient(user.Access, user.Secret)
2014-06-12 00:42:49 +00:00
yml, err := client.GetScript(hook)
2014-06-04 21:25:38 +00:00
if err != nil {
return badRequest{err}
}
c := commit.Commit{
RepoID: repo.ID,
Status: commit.StatusEnqueue,
Sha: hook.Sha,
Branch: hook.Branch,
PullRequest: hook.PullRequest,
Timestamp: hook.Timestamp,
2014-06-12 00:42:49 +00:00
Message: hook.Message,
Config: yml}
2014-06-04 21:25:38 +00:00
c.SetAuthor(hook.Author)
// inser the commit into the database
if err := h.commits.Insert(&c); err != nil {
return badRequest{err}
}
2014-06-12 19:44:19 +00:00
//fmt.Printf("%s", yml)
2014-06-04 21:25:38 +00:00
// drop the items on the queue
2014-06-12 00:42:49 +00:00
h.queue.Add(&queue.BuildTask{Repo: repo, Commit: &c})
2014-06-04 21:25:38 +00:00
return nil
}
func (h *HookHandler) Register(r *pat.Router) {
r.Post("/hook/{host}", errorHandler(h.PostHook))
r.Put("/hook/{host}", errorHandler(h.PostHook))
}