98 lines
2.9 KiB
Go
98 lines
2.9 KiB
Go
package handler
|
|
|
|
import (
|
|
"net/http"
|
|
|
|
"github.com/go-chi/chi/v5"
|
|
"github.com/prabhupadasays/spsays-bff/internal/repository"
|
|
"github.com/prabhupadasays/spsays-bff/pkg/response"
|
|
)
|
|
|
|
type GlossaryHandler struct {
|
|
repo *repository.GlossaryRepo
|
|
}
|
|
|
|
func NewGlossaryHandler(repo *repository.GlossaryRepo) *GlossaryHandler {
|
|
return &GlossaryHandler{repo: repo}
|
|
}
|
|
|
|
// List returns all glossary entries sorted by term.
|
|
// GET /glossary
|
|
func (h *GlossaryHandler) List(w http.ResponseWriter, r *http.Request) {
|
|
docs, err := h.repo.GetAll(r.Context())
|
|
if err != nil {
|
|
response.Error(w, http.StatusInternalServerError, "failed to fetch glossary")
|
|
return
|
|
}
|
|
response.JSON(w, http.StatusOK, docs)
|
|
}
|
|
|
|
// GetByTerm returns a single glossary entry by exact term match.
|
|
// GET /glossary/term/{term}
|
|
func (h *GlossaryHandler) GetByTerm(w http.ResponseWriter, r *http.Request) {
|
|
term := chi.URLParam(r, "term")
|
|
doc, err := h.repo.GetByTerm(r.Context(), term)
|
|
if err != nil {
|
|
response.Error(w, http.StatusInternalServerError, "failed to fetch term")
|
|
return
|
|
}
|
|
if doc == nil {
|
|
response.Error(w, http.StatusNotFound, "term not found")
|
|
return
|
|
}
|
|
response.JSON(w, http.StatusOK, doc)
|
|
}
|
|
|
|
// GetByLetter returns all glossary entries whose term starts with the given
|
|
// base letter (including diacritical variants like Ā→A, Ś→S, etc.).
|
|
// GET /glossary/letter/{letter}
|
|
func (h *GlossaryHandler) GetByLetter(w http.ResponseWriter, r *http.Request) {
|
|
letter := chi.URLParam(r, "letter")
|
|
if len(letter) != 1 {
|
|
response.Error(w, http.StatusBadRequest, "letter must be a single character")
|
|
return
|
|
}
|
|
|
|
docs, err := h.repo.GetByLetter(r.Context(), letter)
|
|
if err != nil {
|
|
response.Error(w, http.StatusInternalServerError, "failed to fetch glossary entries")
|
|
return
|
|
}
|
|
if docs == nil {
|
|
docs = []repository.GlossaryEntryDoc{}
|
|
}
|
|
response.JSON(w, http.StatusOK, docs)
|
|
}
|
|
|
|
// GetTermsByLetter returns lightweight term summaries (no definitions) for a
|
|
// given base letter. Used for sidebar listing.
|
|
// GET /glossary/letter/{letter}/terms
|
|
func (h *GlossaryHandler) GetTermsByLetter(w http.ResponseWriter, r *http.Request) {
|
|
letter := chi.URLParam(r, "letter")
|
|
if len(letter) != 1 {
|
|
response.Error(w, http.StatusBadRequest, "letter must be a single character")
|
|
return
|
|
}
|
|
|
|
docs, err := h.repo.GetTermsByLetter(r.Context(), letter)
|
|
if err != nil {
|
|
response.Error(w, http.StatusInternalServerError, "failed to fetch terms")
|
|
return
|
|
}
|
|
if docs == nil {
|
|
docs = []repository.GlossaryTermSummary{}
|
|
}
|
|
response.JSON(w, http.StatusOK, docs)
|
|
}
|
|
|
|
// GetLetterCounts returns the count of glossary entries per base letter.
|
|
// GET /glossary/letters
|
|
func (h *GlossaryHandler) GetLetterCounts(w http.ResponseWriter, r *http.Request) {
|
|
counts, err := h.repo.GetLetterCounts(r.Context())
|
|
if err != nil {
|
|
response.Error(w, http.StatusInternalServerError, "failed to fetch letter counts")
|
|
return
|
|
}
|
|
response.JSON(w, http.StatusOK, counts)
|
|
}
|