internal/httpd/builds.go
76 lines · 1836 bytes
1package httpd
2
3import (
4 "net/http"
5 "strconv"
6)
7
8// buildView mirrors the build commands' JSON. The templates read these
9// names; nothing here touches the store.
10type buildView struct {
11 Number int64 `json:"number"`
12 Job string `json:"job"`
13 Status string `json:"status"`
14 SHA string `json:"sha"`
15 Ref string `json:"ref"`
16 CreatedAt string `json:"created_at"`
17 FinishedAt string `json:"finished_at"`
18}
19
20type jobView struct {
21 Name string `json:"name"`
22 Schedule string `json:"schedule"`
23 Tags string `json:"tags"`
24}
25
26func (s *Server) builds(w http.ResponseWriter, r *http.Request) {
27 p, ok := s.repoFor(w, r, "")
28 if !ok {
29 return
30 }
31 p.Tab = "builds"
32 viewer := s.webViewer(r)
33
34 var builds []buildView
35 s.runControlInto(viewer, []string{"build", "list", p.Repo.Path()}, &builds)
36
37 // The jobs a trigger can name. A repo without a CI config has none;
38 // that is not an error for this page.
39 var jobs []jobView
40 s.runControlInto(viewer, []string{"build", "jobs", p.Repo.Path()}, &jobs)
41
42 s.render(w, "builds.html", struct {
43 repoPage
44 Builds []buildView
45 Jobs []jobView
46 CanWrite bool
47 Notice string
48 }{p, builds, jobs, s.canWriteRepo(r, p.Repo), r.URL.Query().Get("e")})
49}
50
51func (s *Server) build(w http.ResponseWriter, r *http.Request) {
52 p, ok := s.repoFor(w, r, "")
53 if !ok {
54 return
55 }
56 p.Tab = "builds"
57 if _, err := strconv.ParseInt(r.PathValue("n"), 10, 64); err != nil {
58 s.notFound(w, r)
59 return
60 }
61 n := r.PathValue("n")
62 viewer := s.webViewer(r)
63
64 var b buildView
65 if _, ok := s.runControlInto(viewer, []string{"build", "show", p.Repo.Path(), n}, &b); !ok {
66 s.notFound(w, r)
67 return
68 }
69 log, _, _ := s.runControl(viewer, []string{"build", "log", p.Repo.Path(), n})
70
71 s.render(w, "build.html", struct {
72 repoPage
73 Build buildView
74 Log string
75 }{p, b, log})
76}