Shapeless blog is my personal blogging backend written in Go. It implements a rest service and renders a simple web template.
I wrote it because I want to have a way to write blog posts in Emacs with ease. There are a lot of alternative solutions, but none of them are made for org-mode, most of them are for markdown.
Previously, the traditional way of blogging in org-mode is to use the internal ox-html backend to export into pure html files. However, you cannot have a universal header which you can change without modifying every file. This in the past gave me a lot of headaches.
Shapeless blog is a simple blogging solution in the server side. It accepts HTTP requests to create, update or delete blog posts.
For the api, please refers to this.
Currently, I have only written a client for Emacs, emacs-shapeless-blog.
- Go
- SQLite
git clone https://github.com/drshapeless/shapeless-blog
cd shapeless-blog
make build
sudo make install
If this is your first time starting shapeless-blog, migrate the datebase first.
shapeless-blog -path=~/shapeless-blog.db -migrate
After migration, you can start your service.
shapeless-blog -path=~/shapeless-blog.db -secret="testsecret"
By default, the shapeless-blog listen to port 9398, you can make nginx to point a url into this port.
Currently I have only written a service for OpenRC, shapeless-blog.init. Modify the secret before starting the service, otherwise your secret is known by everyone.
Get a token.
curl -d '{"secret":"testsecret"}' localhost:9398/api/blogging/tokens
In any other api, you should use the token as a bearer token in the HTTP header, e.g. to get the blog post with id 1.
curl -H "Authorization: Bearer <token>" localhost:9398/api/blogging/posts/id/1
The first thing you should do after initializing shapeless-blog is to create three template, with name “post”, “home”, “tag”.
curl -H "Authorization: Bearer <token>" \
-d '{"name": "home", "content": "<your template>"}' \
localhost:9398/api/blogging/templates
They serve for the three view of your website. If you are not going to publish your blog using the internal web structure, omit this part.
The home template receives an object of this.
var body struct {
Posts []*data.Post
Tags []string
}
An array of posts and an array of tags, the posts array consist of the first 100 posts. The tags array is all the unique tags used in the blog posts.
Be careful, the posts in the home template object have an empty content parameter to save resources.
The properly structure the “home” template, you can refer to the sample template.
The post template object is a lot simpler.
type htmlPost struct {
ID int `json:"id"`
Title string `json:"title"`
URL string `json:"url"`
Preview string `json:"preview"`
Tags []string `json:"tags"`
Content template.HTML `json:"content"`
CreateAt string `json:"create_at"`
UpdateAt string `json:"update_at"`
}
See sample.
The tag template object.
var body struct {
Posts []*data.Post
Tag string
}
The posts here also have an empty content body.
See sample.