summaryrefslogtreecommitdiff
path: root/srv/src/post
diff options
context:
space:
mode:
Diffstat (limited to 'srv/src/post')
-rw-r--r--srv/src/post/post.go64
-rw-r--r--srv/src/post/post_test.go32
-rw-r--r--srv/src/post/store.go1
3 files changed, 97 insertions, 0 deletions
diff --git a/srv/src/post/post.go b/srv/src/post/post.go
new file mode 100644
index 0000000..54555c3
--- /dev/null
+++ b/srv/src/post/post.go
@@ -0,0 +1,64 @@
+// Package post deals with the storage and rending of blog post.
+package post
+
+import (
+ "fmt"
+ "path"
+ "regexp"
+ "strings"
+ "time"
+)
+
+// Date represents a calendar date with no timezone information attached.
+type Date struct {
+ Year int
+ Month time.Month
+ Day int
+}
+
+// DateFromTime converts a Time into a Date, truncating all non-date
+// information.
+func DateFromTime(t time.Time) Date {
+ return Date{
+ Year: t.Year(),
+ Month: t.Month(),
+ Day: t.Day(),
+ }
+}
+
+var titleCleanRegexp = regexp.MustCompile(`[^a-z ]`)
+
+// NewID generates a (hopefully) unique ID based on the given title.
+func NewID(title string) string {
+ title = strings.ToLower(title)
+ title = titleCleanRegexp.ReplaceAllString(title, "")
+ title = strings.ReplaceAll(title, " ", "-")
+ return title
+}
+
+// Post contains all information having to do with a blog post.
+type Post struct {
+ ID string
+ Title string
+ Description string
+ Tags []string
+ Series string
+
+ PublishedAt Date
+ LastUpdatedAt Date
+
+ Body string
+}
+
+// URL returns the relative URL of the Post.
+func (p Post) URL() string {
+ return path.Join(
+ fmt.Sprintf(
+ "%d/%0d/%0d",
+ p.PublishedAt.Year,
+ p.PublishedAt.Month,
+ p.PublishedAt.Day,
+ ),
+ p.ID+".html",
+ )
+}
diff --git a/srv/src/post/post_test.go b/srv/src/post/post_test.go
new file mode 100644
index 0000000..47c9ae8
--- /dev/null
+++ b/srv/src/post/post_test.go
@@ -0,0 +1,32 @@
+package post
+
+import (
+ "strconv"
+ "testing"
+
+ "github.com/stretchr/testify/assert"
+)
+
+func TestNewID(t *testing.T) {
+
+ tests := [][2]string{
+ {
+ "Why Do We Have WiFi Passwords?",
+ "why-do-we-have-wifi-passwords",
+ },
+ {
+ "Ginger: A Small VM Update",
+ "ginger-a-small-vm-update",
+ },
+ {
+ "Something-Weird.... woah!",
+ "somethingweird-woah",
+ },
+ }
+
+ for i, test := range tests {
+ t.Run(strconv.Itoa(i), func(t *testing.T) {
+ assert.Equal(t, test[1], NewID(test[0]))
+ })
+ }
+}
diff --git a/srv/src/post/store.go b/srv/src/post/store.go
new file mode 100644
index 0000000..235520f
--- /dev/null
+++ b/srv/src/post/store.go
@@ -0,0 +1 @@
+package post