133 lines
3.4 KiB
Go
133 lines
3.4 KiB
Go
package broadcasters
|
|
|
|
import (
|
|
"context"
|
|
"strings"
|
|
"time"
|
|
|
|
"encore.dev/beta/errs"
|
|
)
|
|
|
|
type ChatLogEntry struct {
|
|
ID int64 `json:"id"`
|
|
Timestamp time.Time `json:"timestamp"`
|
|
Room string `json:"room"`
|
|
Type string `json:"type"`
|
|
Data string `json:"data"`
|
|
}
|
|
|
|
type AddChatLogParams struct {
|
|
Type string `json:"type"`
|
|
Data string `json:"data"`
|
|
}
|
|
|
|
type ListChatLogParams struct {
|
|
Limit int `json:"limit,omitempty" query:"limit"`
|
|
Type string `json:"type,omitempty" query:"type"`
|
|
}
|
|
|
|
type ListChatLogResponse struct {
|
|
Messages []*ChatLogEntry `json:"messages"`
|
|
}
|
|
|
|
// AddChatLog inserisce un nuovo evento o messaggio nella tabella chatlog.
|
|
//
|
|
//encore:api public method=POST path=/broadcasters/id/:id/chatlog
|
|
func AddChatLog(ctx context.Context, id string, p *AddChatLogParams) (*ChatLogEntry, error) {
|
|
if strings.TrimSpace(id) == "" {
|
|
return nil, &errs.Error{Code: errs.InvalidArgument, Message: "id stanza obbligatorio"}
|
|
}
|
|
if p == nil || strings.TrimSpace(p.Data) == "" {
|
|
return nil, &errs.Error{Code: errs.InvalidArgument, Message: "data obbligatorio"}
|
|
}
|
|
|
|
msgType := strings.ToUpper(strings.TrimSpace(p.Type))
|
|
if msgType == "" || msgType == "ADMIN_ALERT" {
|
|
msgType = "MESSAGE"
|
|
} else if msgType == "ALERT" {
|
|
msgType = "ALLERT"
|
|
}
|
|
switch msgType {
|
|
case "ACTION", "MESSAGE", "ALLERT", "CMD":
|
|
default:
|
|
msgType = "MESSAGE"
|
|
}
|
|
|
|
entry := &ChatLogEntry{
|
|
Room: id,
|
|
Type: msgType,
|
|
Data: p.Data,
|
|
}
|
|
|
|
err := db.QueryRow(ctx, `
|
|
INSERT INTO chatlog (room, type, data, timestamp)
|
|
VALUES ($1, $2, $3, NOW())
|
|
RETURNING id, timestamp
|
|
`, entry.Room, entry.Type, entry.Data).Scan(&entry.ID, &entry.Timestamp)
|
|
if err != nil {
|
|
return nil, errs.WrapCode(err, errs.Internal, "impossibile salvare il messaggio di chat")
|
|
}
|
|
|
|
return entry, nil
|
|
}
|
|
|
|
// ListChatLog preleva gli ultimi messaggi per la stanza (default 30) e li ordina
|
|
// in ordine cronologico crescente (dal più vecchio al più recente), pronti per l'append nella UI.
|
|
//
|
|
//encore:api public method=GET path=/broadcasters/id/:id/chatlog
|
|
func ListChatLog(ctx context.Context, id string, p *ListChatLogParams) (*ListChatLogResponse, error) {
|
|
if strings.TrimSpace(id) == "" {
|
|
return nil, &errs.Error{Code: errs.InvalidArgument, Message: "id stanza obbligatorio"}
|
|
}
|
|
|
|
limit := 30
|
|
filterType := ""
|
|
if p != nil {
|
|
if p.Limit > 0 {
|
|
limit = p.Limit
|
|
}
|
|
if t := strings.TrimSpace(p.Type); t != "" {
|
|
filterType = strings.ToUpper(t)
|
|
}
|
|
}
|
|
if limit > 100 {
|
|
limit = 100
|
|
}
|
|
|
|
query := `
|
|
SELECT id, timestamp, room, type, data
|
|
FROM (
|
|
SELECT id, timestamp, room, type, data
|
|
FROM chatlog
|
|
WHERE room = $1 AND ($3 = '' OR type = $3)
|
|
ORDER BY timestamp DESC, id DESC
|
|
LIMIT $2
|
|
) sub
|
|
ORDER BY timestamp ASC, id ASC
|
|
`
|
|
|
|
rows, err := db.Query(ctx, query, id, limit, filterType)
|
|
if err != nil {
|
|
return nil, errs.WrapCode(err, errs.Internal, "impossibile recuperare i messaggi di chat")
|
|
}
|
|
defer rows.Close()
|
|
|
|
var list []*ChatLogEntry
|
|
for rows.Next() {
|
|
var e ChatLogEntry
|
|
if err := rows.Scan(&e.ID, &e.Timestamp, &e.Room, &e.Type, &e.Data); err != nil {
|
|
return nil, errs.WrapCode(err, errs.Internal, "errore nella lettura dei messaggi")
|
|
}
|
|
list = append(list, &e)
|
|
}
|
|
if err := rows.Err(); err != nil {
|
|
return nil, errs.WrapCode(err, errs.Internal, "errore iterazione messaggi")
|
|
}
|
|
|
|
if list == nil {
|
|
list = []*ChatLogEntry{}
|
|
}
|
|
|
|
return &ListChatLogResponse{Messages: list}, nil
|
|
}
|