You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

78 lines
1.4 KiB

// Package tcp provides a plain HTTP transport for the relay.
package tcp
import (
"context"
"fmt"
"net/http"
"sync"
"lol.mleku.dev/log"
)
// Config holds TCP transport configuration.
type Config struct {
// Addr is the listen address (e.g., "0.0.0.0:3334").
Addr string
// Handler is the HTTP handler to serve.
Handler http.Handler
}
// Transport serves HTTP over plain TCP.
type Transport struct {
cfg *Config
server *http.Server
mu sync.Mutex
}
// New creates a new TCP transport.
func New(cfg *Config) *Transport {
return &Transport{cfg: cfg}
}
func (t *Transport) Name() string { return "tcp" }
func (t *Transport) Start(ctx context.Context) error {
t.mu.Lock()
defer t.mu.Unlock()
t.server = &http.Server{
Addr: t.cfg.Addr,
Handler: t.cfg.Handler,
}
log.I.F("starting listener on http://%s", t.cfg.Addr)
errCh := make(chan error, 1)
go func() {
if err := t.server.ListenAndServe(); err != nil && err != http.ErrServerClosed {
errCh <- err
}
close(errCh)
}()
// Give the server a moment to fail on bind errors
select {
case err := <-errCh:
if err != nil {
return fmt.Errorf("tcp listen on %s: %w", t.cfg.Addr, err)
}
default:
}
return nil
}
func (t *Transport) Stop(ctx context.Context) error {
t.mu.Lock()
defer t.mu.Unlock()
if t.server == nil {
return nil
}
return t.server.Shutdown(ctx)
}
func (t *Transport) Addresses() []string {
return []string{"ws://" + t.cfg.Addr + "/"}
}