package server
import (
"embed"
"html/template"
"io/fs"
"net/http"
"os"
"strings"
"forge.cadoles.com/arcad/arcast/pkg/network"
"github.com/dschmidt/go-layerfs"
"github.com/pkg/errors"
"gitlab.com/wpetit/goweb/logger"
_ "embed"
)
var (
//go:embed embed/**
embedFS embed.FS
)
func (s *Server) initLayeredFS() error {
layers := make([]fs.FS, 0)
if s.upperLayerDir != "" {
upperLayer := os.DirFS(s.upperLayerDir)
layers = append(layers, upperLayer)
}
baseLayer, err := fs.Sub(embedFS, "embed")
if err != nil {
return errors.WithStack(err)
}
layers = append(layers, baseLayer)
s.layeredFS = layerfs.New(layers...)
return nil
}
func (s *Server) handleStatic(w http.ResponseWriter, r *http.Request) {
path := r.URL.Path
if strings.HasPrefix(path, "/_templates") {
http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
return
}
http.ServeFileFS(w, r, s.layeredFS, path)
}
func (s *Server) handleIndex(w http.ResponseWriter, r *http.Request) {
type templateData struct {
IPs []string
Port int
TLSPort int
ID string
Apps bool
}
ips, err := network.GetLANIPv4Addrs()
if err != nil {
logger.Error(r.Context(), "could not retrieve lan ip addresses", logger.CapturedE(errors.WithStack(err)))
http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
return
}
d := templateData{
ID: s.instanceID,
IPs: ips,
Port: s.port,
TLSPort: s.tlsPort,
Apps: s.appsEnabled,
}
templates, err := template.New("").ParseFS(s.layeredFS, "_partials/*.gohtml", "_templates/*.gohtml")
if err != nil {
logger.Error(r.Context(), "could not parse template", logger.CapturedE(errors.WithStack(err)))
http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
return
}
if err := templates.ExecuteTemplate(w, "index", d); err != nil {
logger.Error(r.Context(), "could not render index page", logger.CapturedE(errors.WithStack(err)))
}
}