server.go

 1package server
 2
 3import (
 4	"fmt"
 5	"log"
 6
 7	"github.com/charmbracelet/soft-serve/config"
 8	appCfg "github.com/charmbracelet/soft-serve/internal/config"
 9	"github.com/charmbracelet/soft-serve/internal/tui"
10
11	"github.com/charmbracelet/wish"
12	bm "github.com/charmbracelet/wish/bubbletea"
13	gm "github.com/charmbracelet/wish/git"
14	lm "github.com/charmbracelet/wish/logging"
15	"github.com/gliderlabs/ssh"
16)
17
18// Server is the Soft Serve server.
19type Server struct {
20	SSHServer *ssh.Server
21	Config    *config.Config
22	config    *appCfg.Config
23}
24
25// NewServer returns a new *ssh.Server configured to serve Soft Serve. The SSH
26// server key-pair will be created if none exists. An initial admin SSH public
27// key can be provided with authKey. If authKey is provided, access will be
28// restricted to that key. If authKey is not provided, the server will be
29// publicly writable until configured otherwise by cloning the `config` repo.
30func NewServer(cfg *config.Config) *Server {
31	ac, err := appCfg.NewConfig(cfg)
32	if err != nil {
33		log.Fatal(err)
34	}
35
36	// If the host and port are set in config.yaml, and they weren't set in the
37	// environment, update the environment level config accordingly, which is
38	// the config used to start the server.
39	if cfg.Host == "" {
40		cfg.Host = ac.Host
41	}
42	if cfg.Port == 0 {
43		cfg.Port = ac.Port
44	}
45
46	mw := []wish.Middleware{
47		bm.Middleware(tui.SessionHandler(ac)),
48		gm.Middleware(cfg.RepoPath, ac),
49		lm.Middleware(),
50	}
51	s, err := wish.NewServer(
52		ssh.PublicKeyAuth(ac.PublicKeyHandler),
53		ssh.PasswordAuth(ac.PasswordHandler),
54		wish.WithAddress(fmt.Sprintf("%s:%d", cfg.Host, cfg.Port)),
55		wish.WithHostKeyPath(cfg.KeyPath),
56		wish.WithMiddleware(mw...),
57	)
58	if err != nil {
59		log.Fatalln(err)
60	}
61	return &Server{
62		SSHServer: s,
63		Config:    cfg,
64		config:    ac,
65	}
66}
67
68// Reload reloads the server configuration.
69func (srv *Server) Reload() error {
70	return srv.config.Reload()
71}
72
73// Start starts the SSH server.
74func (srv *Server) Start() error {
75	return srv.SSHServer.ListenAndServe()
76}