feat: tag system

This commit is contained in:
2026-02-03 09:41:03 +01:00
parent 3f5cf0d673
commit cb11e34798
11 changed files with 397 additions and 10 deletions

View File

@ -6,6 +6,7 @@ import (
"donniemarko/internal/service"
"html/template"
"net/http"
"net/url"
"strings"
)
@ -34,6 +35,10 @@ func (h *Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
// Handle individual notes
if strings.HasPrefix(path, "/notes/") {
if strings.Contains(path, "/tags") {
h.handleTags(w, r)
return
}
h.handleNotes(w, r)
return
}
@ -160,3 +165,61 @@ func (h *Handler) handleNotes(w http.ResponseWriter, r *http.Request) {
h.templates.Render(w, "index", state)
}
func (h *Handler) handleTags(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodPost {
http.Error(w, "Method not allowed", http.StatusMethodNotAllowed)
return
}
noteID, tag, isRemove := parseTagRoute(r.URL.Path)
if noteID == "" {
http.NotFound(w, r)
return
}
if isRemove {
if tag == "" {
http.Error(w, "Missing tag", http.StatusBadRequest)
return
}
if err := h.notesService.RemoveTag(noteID, tag); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
} else {
if err := r.ParseForm(); err != nil {
http.Error(w, "Invalid form", http.StatusBadRequest)
return
}
tag := r.FormValue("tag")
if tag == "" {
http.Error(w, "Missing tag", http.StatusBadRequest)
return
}
if err := h.notesService.AddTag(noteID, tag); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
}
http.Redirect(w, r, "/notes/"+noteID, http.StatusSeeOther)
}
func parseTagRoute(path string) (noteID string, tag string, isRemove bool) {
parts := strings.Split(strings.Trim(path, "/"), "/")
if len(parts) < 3 || parts[0] != "notes" || parts[2] != "tags" {
return "", "", false
}
noteID = parts[1]
if len(parts) >= 4 {
decoded, err := url.PathUnescape(parts[3])
if err != nil {
return noteID, "", true
}
return noteID, decoded, true
}
return noteID, "", false
}