package main import ( "context" "embed" "fmt" "html/template" "net/http" "strings" "github.com/nbd-wtf/go-nostr" ) // embed ui files //go:embed ui/dist/* var dist embed.FS func inviteTreeHandler(w http.ResponseWriter, r *http.Request) { formattedInviteData := buildHTMLTree(whitelist, "") data := map[string]interface{}{ "Relayname": relayName, "Relaydescription": relayDescription, "Pagetitle": "Invite Hierarchy", "Pagecontent": ` ` + formattedInviteData, } tmpl, err := template.ParseFS(dist, "ui/dist/index.html") if err != nil { http.Error(w, "Error parsing template: "+err.Error(), http.StatusInternalServerError) return } err = tmpl.Execute(w, data) if err != nil { http.Error(w, "Error executing template: "+err.Error(), http.StatusInternalServerError) return } } func reportsViewerHandler(w http.ResponseWriter, r *http.Request) { var formattedReportsData template.HTML = "" events, _ := db.QueryEvents(context.Background(), nostr.Filter{ Kinds: []int{1984}, Limit: 52, }) type Report struct { ID string ByUser string AboutUser string AboutEvent string Type string Content string } for ev := range events { pTag := ev.Tags.GetFirst([]string{"p"}) eTag := ev.Tags.GetFirst([]string{"e"}) if pTag != nil { var typeReport = eTag.Relay()[6:] if typeReport == "" { typeReport = pTag.Relay()[6:] } report := Report{ ID: ev.ID, ByUser: ev.PubKey, AboutUser: pTag.Value(), AboutEvent: eTag.Value(), Type: typeReport, Content: ev.Content, } // get AboutEvent content, note1 ect formattedReportsData += template.HTML(fmt.Sprintf(`

Report %v

By User: %v

About User: %v

`, report.ID, getUserInfo(context.Background(), report.ByUser).Npub, getUserInfo(context.Background(), report.ByUser).Name, getUserInfo(context.Background(), report.AboutUser).Npub, getUserInfo(context.Background(), report.AboutUser).Name, )) if report.AboutEvent != "" { // fetch event data aboutEvents, _ := db.QueryEvents(context.TODO(), nostr.Filter{ IDs: []string{report.AboutEvent}, }) for aboutEvent := range aboutEvents { formattedReportsData += template.HTML(fmt.Sprintf(`

About Event:

`, template.HTMLEscaper(aboutEvent.Kind), template.HTMLEscaper(aboutEvent.Tags), template.HTMLEscaper(aboutEvent.Content), )) } } formattedReportsData += template.HTML(fmt.Sprintf(`

Type: %v

`, report.Type, )) if report.Content != "" { formattedReportsData += template.HTML(fmt.Sprintf(`

Content: %v


`, template.HTMLEscaper(report.Content), template.HTMLEscaper(report.ID), template.HTMLEscaper(report.AboutUser), template.HTMLEscaper(report.ID), template.HTMLEscaper(report.ByUser), )) } } } data := map[string]interface{}{ "Relayname": relayName, "Relaydescription": relayDescription, "Pagetitle": "Reports Viewer", "Pagecontent": formattedReportsData, } tmpl, err := template.ParseFS(dist, "ui/dist/index.html") if err != nil { http.Error(w, "Error parsing template: "+err.Error(), http.StatusInternalServerError) return } // Execute the template with the provided data and write it to the response err = tmpl.Execute(w, data) if err != nil { http.Error(w, "Error executing template: "+err.Error(), http.StatusInternalServerError) return } } func homePageHandler(w http.ResponseWriter, r *http.Request) { relayOwnerInfo := getUserInfo(context.Background(), relayPubkey) data := map[string]interface{}{ "Relayname": relayName, "Relaydescription": relayDescription, "Pagetitle": "Info", "Pagecontent": template.HTML(fmt.Sprintf(`
Relay Name: %v
Relay Description: %v
Relay Owner: %v
Relay Alternative Contact: %v

This relay uses Khatru Invite, which is build with Khatru
`, relayName, relayDescription, relayOwnerInfo.Npub, relayOwnerInfo.Name, relayContact)), } tmpl, err := template.ParseFS(dist, "ui/dist/index.html") if err != nil { http.Error(w, "Error parsing template: "+err.Error(), http.StatusInternalServerError) return } err = tmpl.Execute(w, data) if err != nil { http.Error(w, "Error executing template: "+err.Error(), http.StatusInternalServerError) return } } func redirectHandler(w http.ResponseWriter, r *http.Request) { if strings.HasPrefix(r.URL.Path, "/assets") { staticHandler("ui/dist", w, r) } else if r.URL.Path == "/" { homePageHandler(w, r) } } func staticHandler(prefix string, w http.ResponseWriter, r *http.Request) { path := prefix + r.URL.Path data, err := dist.ReadFile(path) if err != nil { http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound) return } contentType := http.DetectContentType(data) if strings.HasSuffix(r.URL.Path, ".js") { contentType = "application/javascript" } else if strings.HasSuffix(r.URL.Path, ".css") { contentType = "text/css" } w.Header().Set("Content-Type", contentType) if _, err := w.Write(data); err != nil { http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError) return } }