Compare commits
2
Commits
6ce98b4706
...
b06a622c62
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b06a622c62 | ||
|
|
454b9e2502 |
No files matched your search
@@ -1,3 +1,4 @@
|
||||
# handmade-revolt-go
|
||||
|
||||
A ledger of submission requests to handmade revolt.
|
||||
A ledger of submission requests to handmade revolt.
|
||||
Listens to submissions from https://handmadecities.com/revolt, persists them to disk, and notifies the team through ntfy.sh
|
||||
@@ -0,0 +1,94 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
"net/http"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
// NOTE(jmug): Port here is not really important, choose at your convenience.
|
||||
const listenAddr = "127.0.0.1:<TBD>"
|
||||
|
||||
func main() {
|
||||
http.HandleFunc("/", handleSubmit)
|
||||
|
||||
log.Printf("Listening on %s\n", listenAddr)
|
||||
log.Fatal(http.ListenAndServe(listenAddr, nil))
|
||||
}
|
||||
|
||||
func handleSubmit(w http.ResponseWriter, r *http.Request) {
|
||||
if r.Method != http.MethodPost {
|
||||
http.Error(w, "Method not allowed", http.StatusMethodNotAllowed)
|
||||
return
|
||||
}
|
||||
|
||||
if err := r.ParseForm(); err != nil {
|
||||
log.Printf("Error parsing form: %v", err)
|
||||
http.Redirect(w, r, "https://handmadecities.com/revolt/error", http.StatusSeeOther)
|
||||
return
|
||||
}
|
||||
|
||||
name := r.FormValue("name")
|
||||
email := r.FormValue("email")
|
||||
website := r.FormValue("website")
|
||||
reason := r.FormValue("reason")
|
||||
|
||||
// Basic validation
|
||||
if name == "" || email == "" {
|
||||
log.Println("Missing required fields")
|
||||
http.Redirect(w, r, "https://handmadecities.com/", http.StatusSeeOther)
|
||||
return
|
||||
}
|
||||
|
||||
if err := appendToFile(name, email, website, reason); err != nil {
|
||||
log.Printf("Error writing to file: %v", err)
|
||||
http.Redirect(w, r, "https://handmadecities.com/", http.StatusSeeOther)
|
||||
return
|
||||
}
|
||||
|
||||
log.Printf("New application from: %s <%s>", name, email)
|
||||
http.Redirect(w, r, "https://handmadecities.com/revolt-success", http.StatusSeeOther)
|
||||
|
||||
// Send ntfy alert
|
||||
// NOTE(jmug): request secret from shhh, `revol-submission-ntfy-fqdn`
|
||||
_, err := http.Post(
|
||||
"<redacted>",
|
||||
"text/plain",
|
||||
strings.NewReader(fmt.Sprintf("New Revolt application from %s", name)),
|
||||
)
|
||||
|
||||
if err != nil {
|
||||
log.Printf("Failed to send ntfy alert: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
// NOTE(jmug): I think this is fine for now, but crazy idea: How about a simple
|
||||
// sqlite db, a cli, and mTLS auth so that an operator (Abner) can query submissions
|
||||
// without jumping on the server.
|
||||
func appendToFile(name, email, website, reason string) error {
|
||||
home, err := os.UserHomeDir()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
filePath := filepath.Join(home, "revolt_applications.txt")
|
||||
|
||||
f, err := os.OpenFile(filePath, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer f.Close()
|
||||
|
||||
entry := fmt.Sprintf(
|
||||
"--- %s ---\nName: %s\nEmail: %s\nWebsite: %s\nReason: %s\n\n",
|
||||
time.Now().Format(time.RFC1123),
|
||||
name, email, website, reason,
|
||||
)
|
||||
|
||||
_, err = f.WriteString(entry)
|
||||
return err
|
||||
}
|
||||
Reference in new issue
Block a user