package main import ( "log" "fmt" "strings" "io/fs" "path/filepath" "os" "github.com/gofiber/fiber/v2" "github.com/gofiber/template/html/v2" "zedshaw.games/ssgod/config" ) func Fail(err error, format string, v ...any) error { err_format := fmt.Sprintf("ERROR: %v; %s", err, format) log.Printf(err_format, v...) return err } func ProcessDirEntry(engine *html.Engine, path string, d fs.DirEntry, err error) error { settings := config.Settings if !d.IsDir() { if err != nil { return Fail(err, "path: %s", path); } dir := filepath.Dir(path) err = os.MkdirAll(dir, 0750) if err != nil { return Fail(err, "making dir %s", dir); } split_path := strings.Split(path, string(os.PathSeparator))[1:] source_name := strings.Join(split_path, "/") // Render wants / even on windows ext := filepath.Ext(source_name) template_name, found := strings.CutSuffix(source_name, ext) if found && ext == ".html" && template_name != settings.Layout { prefixed_path := append([]string{settings.Target}, split_path...) target_path := filepath.Join(prefixed_path...) _, err := os.Stat(target_path) if os.IsNotExist(err) { target_dir := filepath.Dir(target_path) log.Println("MAKING: ", target_dir) os.MkdirAll(target_dir, 0750) } // TODO: compare time stamps and skip if not newer out, err := os.OpenFile(target_path, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0644) if err != nil { return Fail(err, "writing file %s", target_path) } // generate a data-testid for all pages based on template name page_id := strings.ReplaceAll(template_name, "/", "-") + "-page" err = engine.Render(out, template_name, fiber.Map{"PageId": page_id}, settings.Layout) if err != nil { return Fail(err, "failed to render %s", path) } log.Printf("RENDER: %s -> %s", template_name, target_path) out.Close() } } return nil } func RenderPages() { engine := html.New(config.Settings.Views, ".html") engine.Load() err := filepath.WalkDir(config.Settings.Views, func (path string, d fs.DirEntry, err error) error { return ProcessDirEntry(engine, path, d, err) }) if err != nil { log.Fatalf("can't walk content") } } func main() { config.Load("ssgod.toml") log.Printf("views=%s, layouts=%s, target=%s", config.Settings.Views, config.Settings.Layout, config.Settings.Target) RenderPages() }