initial post 01.01.1970
how this thing is built
templates
<!-- base.html -->
{{define "header"}}
<!DOCTYPE html>
<html lang="en">
<head>
...
</head>
<body>
...
{{end}}
{{define "footer"}}
</main>
<footer>
...
</footer>
</body>
</html>
{{end}}
<!-- post.html -->
{{define "post"}}
{{template "header"}}
<h1>{{.Title}} {{.Timestamp.Format "02.01.2006"}}</h1>
<hr>
{{.Content}}
{{template "footer"}}
{{end}}
//go:embed templates/*.html
var templatesFS embed.FS
var templates = template.Must(template.ParseFS(must(fs.Sub(templatesFS, "templates")), "*.html"))
mux.HandleFunc("/404", func(w http.ResponseWriter, r *http.Request) {
_ = templates.ExecuteTemplate(w, "404", nil)
})
posts
const (
dateFormat = "02.01.2006"
)
//go:embed *.md
var postsFS embed.FS
var (
postNameRE = regexp.MustCompile(`^(?P<date>\d{2}\.\d{2}\.\d{4})-(?P<title>[^.]+)\.md$`)
)
var Posts = map[string]Post{}
func init() {
converter := goldmark.New(
goldmark.WithExtensions(
extension.GFM,
highlighting.NewHighlighting(
highlighting.WithStyle("monokai"),
),
),
goldmark.WithParserOptions(
parser.WithAutoHeadingID(),
),
goldmark.WithRendererOptions(
html.WithHardWraps(),
html.WithXHTML(),
),
)
if err := fs.WalkDir(postsFS, ".", func(path string, d fs.DirEntry, err error) error {
if err != nil {
return err
}
if d.IsDir() {
return nil
}
content, err := postsFS.ReadFile(path)
if err != nil {
return err
}
var buf bytes.Buffer
if err := converter.Convert(content, &buf); err != nil {
return err
}
tokens := postNameRE.FindStringSubmatch(path)
rawDate := tokens[postNameRE.SubexpIndex("date")]
rawTitle := tokens[postNameRE.SubexpIndex("title")]
date, err := time.Parse(dateFormat, rawDate)
if err != nil {
return err
}
id := rawDate + rawTitle
Posts[id] = Post{
ID: id,
Timestamp: date,
Title: strings.ReplaceAll(rawTitle, "_", " "),
Content: template.HTML(buf.String()),
}
return nil
}); err != nil {
panic(err)
}
}
type Post struct {
ID string
Timestamp time.Time
Title string
Content template.HTML
}
deploy
GOOS=linux GOARCH=amd64 go build
ssh larynjahor@home "sudo systemctl stop blog"
scp blogo home:/opt/blog
ssh larynjahor@home "sudo systemctl start blog"