Files

147 lines
3.9 KiB
Go

package api
import (
"errors"
"log/slog"
"net/http"
"time"
"github.com/go-chi/chi/v5"
"github.com/go-chi/render"
"github.com/google/uuid"
)
func GetChannel(w http.ResponseWriter, r *http.Request) {
slog.Debug("channel: entering GetChannel handler")
channelID := chi.URLParam(r, "channelID")
parsed, err := uuid.Parse(channelID)
if err != nil {
render.Render(w, r, ErrInvalidRequest(err))
return
}
channel, err := dbGetChannel(parsed.String())
if err != nil {
if errors.Is(err, ErrChannelNotFound) {
render.Render(w, r, ErrNotFound)
} else {
slog.Error("channel: failed to fetch channel", "channelid", parsed.String(), "error", err)
render.Render(w, r, ErrInternal(err))
}
return
}
slog.Debug("channel: rendering channel", "channelid", channel.ID, "channelname", channel.Name)
if err := render.Render(w, r, NewChannelPayloadResponse(channel)); err != nil {
slog.Error("channel: failed to render channel", "channelid", parsed.String(), "error", err)
render.Render(w, r, ErrInternal(err))
}
}
func ListChannels(w http.ResponseWriter, r *http.Request) {
slog.Debug("channel: entering ListChannels handler")
dbChannels, err := dbGetAllChannels()
if err != nil {
if errors.Is(err, ErrChannelNotFound) {
render.Render(w, r, ErrNotFound)
} else {
slog.Error("channel: failed to fetch channels", "error", err)
render.Render(w, r, ErrInternal(err))
}
return
}
slog.Debug("channel: successfully fetched channels", "count", len(dbChannels))
if err := render.RenderList(w, r, NewChannelListResponse(dbChannels)); err != nil {
slog.Error("channel: failed to render channel list response", "error", err)
render.Render(w, r, ErrInternal(err))
return
}
}
func newChannelID() uuid.UUID {
return uuid.New()
}
func NewChannel(w http.ResponseWriter, r *http.Request) {
slog.Debug("channel: entering NewChannel handler")
err := r.ParseMultipartForm(64 << 10)
if err != nil {
slog.Error("channel: failed to parse multipartform", "error", err)
http.Error(w, "Unable to parse form", http.StatusBadRequest)
return
}
newChannelName := r.FormValue("name")
newChannelType := r.FormValue("type")
newChannelLocation := r.FormValue("location")
newChannelNotes := r.FormValue("notes")
if newChannelName == "" {
slog.Error("channel: channelname is empty")
http.Error(w, "Channel name cannot be empty", http.StatusBadRequest)
return
}
newChannel := Channel{
ID: newChannelID(),
Name: newChannelName,
Created: time.Now(),
Type: newChannelType,
Location: newChannelLocation,
Notes: newChannelNotes,
}
slog.Debug("channel: adding new channel to database", "channelid", newChannel.ID, "channelname", newChannel.Name)
err = dbAddChannel(&newChannel)
if err != nil {
slog.Error("channel: failed to add new channel", "channelid", newChannel.ID, "channelname", newChannel.Name)
render.Render(w, r, ErrInternal(err))
return
}
slog.Debug("channel: successfully added new channel", "channelid", newChannel.ID, "channelname", newChannel.Name)
render.Render(w, r, NewChannelPayloadResponse(&newChannel))
}
func DeleteChannel(w http.ResponseWriter, r *http.Request) {
slog.Debug("channel: entering DeleteChannel handler")
channelID := chi.URLParam(r, "channelID")
parsed, err := uuid.Parse(channelID)
if err != nil {
render.Render(w, r, ErrInvalidRequest(err))
return
}
err = dbDeleteChannel(parsed.String())
if err != nil {
if errors.Is(err, ErrChannelNotFound) {
render.Render(w, r, ErrNotFound)
} else {
slog.Error("channel: failed to delete channel", "channelid", parsed.String(), "error", err)
render.Render(w, r, ErrInternal(err))
}
return
}
slog.Debug("channel: deleted channel", "channelid", parsed.String())
w.Write([]byte("Channel deleted successfully"))
}
type Channel struct {
ID uuid.UUID
Name string
Created time.Time
Type string
Location string
Notes string
}
type channelKey struct{}
type ChannelPayload struct {
*Channel
}