Implement GROUP command

This commit is contained in:
ChronosX88 2022-01-25 19:27:58 +03:00
parent 796f37d55c
commit ee63c0a9ef
Signed by: ChronosXYZ
GPG Key ID: 085A69A82C8C511A
6 changed files with 47 additions and 1 deletions

View File

@ -21,7 +21,7 @@
- :heavy_check_mark: `QUIT`
- :x: `ARTICLE`
- :x: `BODY`
- :x: `GROUP`
- :heavy_check_mark: `GROUP`
- :x: `HDR`
- :x: `HEAD`
- :x: `HELP`

View File

@ -83,3 +83,8 @@ func (sb *SQLiteBackend) GetGroupLowWaterMark(g models.Group) (int, error) {
var waterMark int
return waterMark, sb.db.Get(&waterMark, "SELECT article_id FROM articles_to_groups WHERE group_id = ? ORDER BY article_id LIMIT 1", g.ID)
}
func (sb *SQLiteBackend) GetGroup(groupName string) (models.Group, error) {
var group models.Group
return group, sb.db.Get(&group, "SELECT * FROM groups WHERE group_name = ?", groupName)
}

View File

@ -9,6 +9,7 @@ const (
type StorageBackend interface {
ListGroups() ([]models.Group, error)
ListGroupsByPattern(pattern string) ([]models.Group, error)
GetGroup(groupName string) (models.Group, error)
GetArticlesCount(g models.Group) (int, error)
GetGroupLowWaterMark(g models.Group) (int, error)
GetGroupHighWaterMark(g models.Group) (int, error)

View File

@ -11,6 +11,7 @@ const (
CommandDate = "DATE"
CommandMode = "MODE"
CommandList = "LIST"
CommandGroup = "GROUP"
)
const (
@ -34,4 +35,5 @@ const (
MessageErrorHappened = "403 Failed to process command:"
MessageListOfNewsgroupsFollows = "215 list of newsgroups follows"
MessageSyntaxError = "501 Syntax Error"
MessageNoSuchGroup = "411 No such newsgroup"
)

View File

@ -1,6 +1,7 @@
package server
import (
"database/sql"
"fmt"
"github.com/ChronosX88/yans/internal/backend"
"github.com/ChronosX88/yans/internal/models"
@ -23,6 +24,7 @@ func NewHandler(b backend.StorageBackend) *Handler {
protocol.CommandQuit: h.handleQuit,
protocol.CommandList: h.handleList,
protocol.CommandMode: h.handleModeReader,
protocol.CommandGroup: h.handleGroup,
}
return h
}
@ -143,6 +145,39 @@ func (h *Handler) handleModeReader(s *Session, arguments []string, id uint) erro
return s.tconn.PrintfLine(protocol.MessageReaderModePostingProhibited) // TODO vary on auth status
}
func (h *Handler) handleGroup(s *Session, arguments []string, id uint) error {
s.tconn.StartResponse(id)
defer s.tconn.EndResponse(id)
if len(arguments) == 0 || len(arguments) > 1 {
return s.tconn.PrintfLine(protocol.MessageSyntaxError)
}
g, err := h.backend.GetGroup(arguments[0])
if err != nil {
if err == sql.ErrNoRows {
return s.tconn.PrintfLine(protocol.MessageNoSuchGroup)
}
return err
}
highWaterMark, err := h.backend.GetGroupHighWaterMark(g)
if err != nil {
return err
}
lowWaterMark, err := h.backend.GetGroupLowWaterMark(g)
if err != nil {
return err
}
articlesCount, err := h.backend.GetArticlesCount(g)
if err != nil {
return err
}
s.currentGroup = &g
return s.tconn.PrintfLine("211 %d %d %d %s", articlesCount, lowWaterMark, highWaterMark, g.GroupName)
}
func (h *Handler) Handle(s *Session, message string, id uint) error {
splittedMessage := strings.Split(message, " ")
for i, v := range splittedMessage {

View File

@ -2,6 +2,7 @@ package server
import (
"context"
"github.com/ChronosX88/yans/internal/models"
"github.com/ChronosX88/yans/internal/protocol"
"io"
"log"
@ -24,6 +25,8 @@ type Session struct {
id string
closed chan<- bool
h *Handler
currentGroup *models.Group
mode SessionMode
}