package main import ( "bytes" "fmt" "html/template" "io" "log" "log/slog" "net/http" etcd "go.etcd.io/etcd/client/v3" ) var version = "v0.0.0" var indexTemplate = template.Must(template.New("index").Parse(`
{{ .message }}
Version {{ .version }}
`)) var etcdClient *etcd.Client func main() { slog.Info("app starting", "version", version) { c, err := etcd.NewFromURL("http://etcd:2379") if err != nil { log.Fatal("etcd: failed to connect: ", err) } etcdClient = c } http.HandleFunc("/", renderTemplate) http.ListenAndServe(":80", nil) } func renderTemplate(w http.ResponseWriter, req *http.Request) { // check request if req.Method+" "+req.URL.Path != "GET /" { http.NotFound(w, req) return } // helper to get a key var err error ctx := req.Context() get := func(key string) (s string) { if err != nil { return "" } resp, getErr := etcdClient.KV.Get(ctx, key) if getErr != nil { err = getErr return } if len(resp.Kvs) == 0 { err = fmt.Errorf("no ") return } return string(resp.Kvs[0].Value) } // fetch the data data := map[string]string{ "title": get("title"), "message": get("message"), "version": version, } if err != nil { slog.Error("failed to get data", "error", err) http.Error(w, "failed to get data", http.StatusInternalServerError) return } // render the template buf := new(bytes.Buffer) err = indexTemplate.Execute(buf, data) if err != nil { slog.Error("failed to render index", "error", err) http.Error(w, "failed to render index", http.StatusInternalServerError) return } io.Copy(w, buf) }