You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
95 lines
1.6 KiB
Go
95 lines
1.6 KiB
Go
|
2 weeks ago
|
package core
|
||
|
|
|
||
|
|
import (
|
||
|
|
"bufio"
|
||
|
|
"context"
|
||
|
|
"fmt"
|
||
|
|
"log/slog"
|
||
|
|
"net"
|
||
|
|
)
|
||
|
|
|
||
|
|
type Server struct {
|
||
|
|
l *slog.Logger
|
||
|
|
port string
|
||
|
|
ctx context.Context
|
||
|
|
Sessions chan *Session
|
||
|
|
ln net.Listener
|
||
|
|
}
|
||
|
|
|
||
|
|
func NewServer(ctx context.Context, l *slog.Logger, port string) *Server {
|
||
|
|
var s Server
|
||
|
|
|
||
|
|
// TODO: Check for context cancellation and cleanup
|
||
|
|
|
||
|
|
c := make(chan *Session)
|
||
|
|
s.Sessions = c
|
||
|
|
ln, err := net.Listen("tcp", port)
|
||
|
|
if err != nil {
|
||
|
|
s.l.With(
|
||
|
|
slog.Any("error", err),
|
||
|
|
).Error("could not start tcp listener")
|
||
|
|
return &s
|
||
|
|
}
|
||
|
|
|
||
|
|
s.ctx = ctx
|
||
|
|
s.ln = ln
|
||
|
|
s.l = l
|
||
|
|
s.port = port
|
||
|
|
|
||
|
|
return &s
|
||
|
|
}
|
||
|
|
|
||
|
|
func (s *Server) Start() {
|
||
|
|
s.l.Debug("starting telnet server")
|
||
|
|
// TODO: Check for context cancellation and cleanup
|
||
|
|
for {
|
||
|
|
conn, err := s.ln.Accept()
|
||
|
|
if err != nil {
|
||
|
|
s.l.With(
|
||
|
|
slog.Any("error", err),
|
||
|
|
).Error("could not accept tcp connection")
|
||
|
|
}
|
||
|
|
s.Sessions <- NewSession(s.ctx, conn, Printer{}, s.l)
|
||
|
|
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
type Session struct {
|
||
|
|
c net.Conn
|
||
|
|
ctx context.Context
|
||
|
|
p Printer
|
||
|
|
l *slog.Logger
|
||
|
|
|
||
|
|
userID uint64
|
||
|
|
}
|
||
|
|
|
||
|
|
func NewSession(ctx context.Context, c net.Conn, p Printer, l *slog.Logger) *Session {
|
||
|
|
return &Session{
|
||
|
|
ctx: ctx,
|
||
|
|
l: l,
|
||
|
|
p: p,
|
||
|
|
c: c,
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
func (s *Session) Start() {
|
||
|
|
s.l.Debug("starting telnet session")
|
||
|
|
fmt.Fprint(s.c, "Welcome to Bing Bong.\n")
|
||
|
|
scanner := bufio.NewScanner(s.c)
|
||
|
|
var line string
|
||
|
|
for {
|
||
|
|
select {
|
||
|
|
case <-s.ctx.Done():
|
||
|
|
s.l.Error("cancelled")
|
||
|
|
return
|
||
|
|
default:
|
||
|
|
if scanner.Scan() {
|
||
|
|
line = scanner.Text()
|
||
|
|
fmt.Fprintf(s.c, "> %q\n", line)
|
||
|
|
}
|
||
|
|
// a.L.Info("scanning input")
|
||
|
|
s.l.With(slog.String("input", line)).Info("received command")
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|