用Makefile搭建博客

缘起

我几乎不会 HTML,不会使用 Perl、Python 的库,不会 PHP 和 Ruby,不懂 JavaScript,但也想搭个博客。

尝试 WordPress

首先选择的是 WordPress,基本上是照着 这篇文章 做的,在 tusooa 和 phoenixlzx 的大力帮助下,注册了个 .tk 的域名和一个免费服务器,基本上算是搭起来了。不过有些不满意的地方,最讨厌的是它不是用标记语言写的,有些繁琐。

尝试 DokuWiki

MeaCulpa 推荐使用 DokuWiki,看了它的一些介绍,觉得这个标记语言还不错。但要让它变成 blog,还是有不少工作要做。要装一个名为 BlogTNG 的插件,我装了之后就只显示空白页了,用 findbad.php 也找不出原因。也用了 lainme 的可以正常工作的 BlogTNG 插件,但在我这儿就是不行。无奈之下还是放弃了。

自己写 Makefile

作为一个 Emacs 用户,得用 Org Mode 做标记语言,其实通过配置 org-publish 应该也能实现的。但我不大会 Elisp,也不熟悉 Org Mode,所以要找其他工具来做发布的任务。我发现了一个叫做 blorgit 的博客系统,跟着教程一步步做,默认页面不怎么样。而且它是 Ruby 写的,我配置不来,于是这个也放弃了。最后选择了用 Makefile 自己写。

基本思路

.org 存放实际写的文章,用于生成 .html,首页 index.html 是文章列表。还要使用第三方的评论系统。

设计

目录设计如下: - 创建目录 2011/07/12/ 来表示当天写的文章(当前还有其他日期,这里使用 2011/07/12/ 只是为了方便阐述) - 2011/07/12/ 下创建 blogging-with-makefile.org ,用于生成 blogging-with-makefile.html - 2011/ 下创建 titles-07 缓存2011年7月所有文章的标题

文章部分就用如上形式储存。所有文章都有共用的页头、页脚(我不知道准确的术语),比如本页上方的的链接和下方 disqus 的评论系统,它们分别储存为 header.org 和 footer.org 。当要把某篇文章的 .org 导出为 .html 时,在前面包含 header.org ,后面包含 footer.org 。 disqus 要求每个网页要包含几个特定的变量,所以 footer.org 需要做下修改再包含。

首页是所有文章的列表,需要用脚本生成出来,还要注意的是它不需要评论系统,所以不包含 footer.org ,

Makefile

Makefile 的主要规则如下:

  • 2011/titles-07 依赖 2011/07/ ,如果该目标过期(需要重建), 那么尝试重建 2011/07/12/ 下所有日期的所有 .html 。然后把这些 .html 的标题抽取出来, 写入 2011/titles-07
  • %.html 依赖 %.org 以及页头页脚,需要用 Org Mode 根据 .org 生成 .html。 这个规则也对首页 index.org 有效。

当 2011/07/12/ 创建后, 2011/titles-07 就会过期,重建 2011/07/12/ 下所有日期的所有过期的 .html ,并且生成新的 2011/titles-07 ,进而 重建 index.org ,最后重建 index.html 。

注意到这种设计把目录作为了依赖,我们要知道目录的修改时间是不会因为被它包含的文件的修改而改变的。所以当 2011/07/12/blogging-with-makefile.org 修改之后, 2011/07/12/ 和 年/月/ 的修改时间都是不会变化的。这样就会导致 2011/07/12/blogging-with-makefile.org 修改后,执行 make 时 2011/07/12/blogging-with-makefile.org 不会得到更新。

为了处理这种情况,我们需要让目录随着被它包含的文件的修改而更新修改时间。我想到的办法是用 inotify,当 2011/07/12/blogging-with-makefile.org 修改之后,自动 touch 年/月/ 。