aboutsummaryrefslogtreecommitdiff
path: root/tools/govanity/main.go
diff options
context:
space:
mode:
Diffstat (limited to 'tools/govanity/main.go')
-rw-r--r--tools/govanity/main.go121
1 files changed, 121 insertions, 0 deletions
diff --git a/tools/govanity/main.go b/tools/govanity/main.go
new file mode 100644
index 0000000..dd6d653
--- /dev/null
+++ b/tools/govanity/main.go
@@ -0,0 +1,121 @@
+package main
+
+import (
+ "bytes"
+ "embed"
+ "flag"
+ "html/template"
+ "io/ioutil"
+ "log"
+ "net/http"
+ "strings"
+
+ "gopkg.in/yaml.v3"
+)
+
+//go:embed templates
+var tpls embed.FS
+
+type repository struct {
+ Name string `yaml:"name"`
+ Repo string `yaml:"repo"`
+}
+
+type config struct {
+ BaseUrl string `yaml:"baseUrl"`
+ VCS string `yaml:"vcs"`
+ Repositories []repository `yaml:"repositories"`
+}
+
+type moduleTmpl struct {
+ Name string
+ Repo string
+ VCS string
+ BaseUrl string
+}
+
+func main() {
+ flag.Parse()
+ buf, err := ioutil.ReadFile("vanity.yaml")
+ if err != nil {
+ log.Fatalf("failed to read the configuration: %+v", err)
+ }
+
+ cfg := &config{}
+ err = yaml.Unmarshal(buf, cfg)
+ if err != nil {
+ log.Fatalf("failed to parse the YAML configuration: %+v", err)
+ }
+
+ http.HandleFunc("/healthz", func(w http.ResponseWriter, r *http.Request) {
+ w.WriteHeader(200)
+ w.Write([]byte("ok"))
+ })
+
+ http.HandleFunc("/", goGet(cfg))
+
+ log.Printf("starting web server on :8080")
+ log.Fatal(http.ListenAndServe(":8080", nil))
+}
+
+func goGet(cfg *config) http.HandlerFunc {
+ return func(w http.ResponseWriter, r *http.Request) {
+ if r.Method != http.MethodGet {
+ status := http.StatusMethodNotAllowed
+ http.Error(w, http.StatusText(status), status)
+ return
+ }
+
+ if r.FormValue("go-get") == "1" {
+ pathParts := strings.Split(r.URL.Path, "/")
+ for _, m := range cfg.Repositories {
+ if pathParts[1] == m.Name {
+ goGetModule(w, r, m, cfg)
+ return
+ }
+ }
+ status := http.StatusNotFound
+ http.Error(w, http.StatusText(status), status)
+ return
+ }
+ browserURL(w, r, cfg)
+ }
+}
+
+func goGetModule(w http.ResponseWriter, r *http.Request, m repository, cfg *config) {
+ tmpl, err := template.ParseFS(tpls, "templates/module.html.tpl")
+ if err != nil {
+ log.Fatal(err)
+ }
+ mod := moduleTmpl{
+ VCS: cfg.VCS,
+ BaseUrl: cfg.BaseUrl,
+ Name: m.Name,
+ Repo: m.Repo,
+ }
+ var buf bytes.Buffer
+ if err := tmpl.Execute(&buf, mod); err != nil {
+ log.Printf("error: %+v", err)
+ status := http.StatusInternalServerError
+ http.Error(w, http.StatusText(status), status)
+ } else {
+ w.Header().Set("Cache-Control", "no-store")
+ w.Write(buf.Bytes())
+ }
+}
+
+func browserURL(w http.ResponseWriter, r *http.Request, cfg *config) {
+ tmpl, err := template.ParseFS(tpls, "templates/index.html.tpl")
+ if err != nil {
+ log.Fatal(err)
+ }
+ var buf bytes.Buffer
+ if err := tmpl.Execute(&buf, cfg); err != nil {
+ log.Printf("error: %+v", err)
+ status := http.StatusInternalServerError
+ http.Error(w, http.StatusText(status), status)
+ } else {
+ w.Header().Set("Cache-Control", "no-store")
+ w.Write(buf.Bytes())
+ }
+}