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
18type Server struct {
19	SSHServer *ssh.Server
20	Config    *config.Config
21	config    *appCfg.Config
22}
23
24// NewServer returns a new *ssh.Server configured to serve Soft Serve. The SSH
25// server key-pair will be created if none exists. An initial admin SSH public
26// key can be provided with authKey. If authKey is provided, access will be
27// restricted to that key. If authKey is not provided, the server will be
28// publicly writable until configured otherwise by cloning the `config` repo.
29func NewServer(cfg *config.Config) *Server {
30	ac, err := appCfg.NewConfig(cfg)
31	if err != nil {
32		log.Fatal(err)
33	}
34	mw := []wish.Middleware{
35		bm.Middleware(tui.SessionHandler(ac)),
36		gm.Middleware(cfg.RepoPath, ac),
37		lm.Middleware(),
38	}
39	s, err := wish.NewServer(
40		ssh.PublicKeyAuth(ac.PublicKeyHandler),
41		ssh.PasswordAuth(ac.PasswordHandler),
42		wish.WithAddress(fmt.Sprintf("%s:%d", cfg.Host, cfg.Port)),
43		wish.WithHostKeyPath(cfg.KeyPath),
44		wish.WithMiddleware(mw...),
45	)
46	if err != nil {
47		log.Fatalln(err)
48	}
49	return &Server{
50		SSHServer: s,
51		Config:    cfg,
52		config:    ac,
53	}
54}
55
56func (srv *Server) Reload() error {
57	return srv.config.Reload()
58}
59
60func (srv *Server) Start() error {
61	return srv.SSHServer.ListenAndServe()
62}