新站点架设过程

为何要重新建站?新站建在哪里?

在忍受了笨重的 Wordpress 三年后(以及 Bluehost 充满 2003 年设计感的管理面板),我终于决定放弃旧站另起炉灶。我对 Wordpress 博客主要有这些不满:

  • 体积庞大,占用很多不必要的服务器空间。
  • 没法使用我熟悉的工具来方便地备份。
  • 没有良好的命令行界面,而命令行正在成为我做任何事情的首选工具。
  • 缺少一些我所需要的基本功能,比如多语言支持。在部分人手里 WordPress 或许极为强大,但是我不想投入时间学习 CSS/js/php ,也不想从那些源头不明的 WordPress 插件商店里下载任何东西。
  • 这些 WordPress 主题/插件商店让我想起 Ubuntu 软件中心。
  • WordPress 有很多我用不到的功能,比如用户系统。这用在个人博客上显然是杀鸡用牛刀。

在我确定了自己的需求后,我很容易地就找到了替代品:一个用我所知道的编程语言(或者我愿意学习的编程语言)所实现的快而小巧并带有原生多语言支持的静态站点生成器,那就是 hugo

至于站点托管服务,我本来考虑使用 github pages 或 netlify 这种简单快速的解决办法,但是考虑到是个人站点,还是 VPS 这种功能强大一些的选择比较合适。而且 github pages 不支持自定义域名的 https ,这对我来说无法接受。我列出了所有比较出名的 VPS 服务提供商,筛出支持 Arch Linux 的部分,最后选择了 DigitalOcean 。由于我想要完全切断和 Bluehost 的联系,我把自己的域名也转移到了 Google Domains 。

安装 Arch Linux

注意 Arch Linux 其实并不适合用作服务器操作系统。如果一切以系统稳定性为优先,那么选择一个非滚动更新的 Linux 发行版比较合适。我在服务器上用 Arch Linux 主要是因为我在我的所有其他电脑上也都运行 Arch Linux。如果你选择使用 Arch Linux 作为服务器操作系统,最好勤于备份:虽然我还没遇到这种情况,但是常有人抱怨 Arch Linux 很容易被玩坏。

安装系统

显然我得到的关于 DigitalOcean 支持 Arch Linux 的情报已经过时了,他们已经停止支持 Arch Linux 有一阵子了。好在有 digitalocean-debian-to-arch ,使得在水滴( droplet , DigitalOcean 对每个服务器的称呼)上安装 Arch Linux 并不困难。我只需要 新建一个 droplet ,通过 ssh 登录服务器,并执行:

# wget https://raw.githubusercontent.com/gh2o/digitalocean-debian-to-arch/debian9/install.sh -O install.sh
# bash install.sh

系统设置

上述安装完成后,我的 droplet 上就有了带有网络的 Arch Linux 。绝大部分的额外设置都可以在 Arch Wiki 找到。我并没有想把这篇日志写成完整的教程,所以细节部分最好参考 Arch Wiki。记录在这篇日志里的指令只是做个人记录之用。

系统时钟

同步系统时钟并设置时区。

# timedatectl set-ntp true
# timedatectl settimezone <Region>/<City>

安装基础软件包

安装/升级 basebase-devel 软件包。

# pacman -S base base-devel

Fstab

生成 fstab

# genfstab -U / >> /etc/fstab

设置系统语言环境

/etc/locale.conf 里去掉 en_US.UTF-8 UTF-8 的注释,然后运行:

locale-gen

/etc/locale.conf 里设置 LANG=en_US.UTF-8

主机名

编辑 /etc/hosts 以加入水滴的主机名:

127.0.1.1    <hostname>.localdomain <hostname>

引导加载程序和 Initramfs

针对英特尔处理器的优化:

# pacman -S intel-ucode
# grub-mkconfig -o /boot/grub/grub.cfg

在 initramfs 里加入 crc32 模组,不然可能导致水滴无法启动。编辑 /etc/mkinitcpio.conf

MODULES= "crc32 libcrc32c crc32c_generic crc32c-intel crc32-pclmul"

重新生成 initramfs 镜像。

# mkinitcpio -p linux

Root 用户密码

你懂的。

# passwd

用户设置

这是一些让 Arch Linux 使用起来更加友好的设置。

创建用户帐号

显然只使用 root 帐号不是什么好主意:

# useradd -m -G wheel -s /bin/bash <username>
# passwd <username>

把用户加入 Sudoer

编辑 /etc/sudoers 并加入:

<username> ALL=(ALL) ALL

以用户身份登录

剩下的设置都会以用户身份执行:

# su <username>

软件包管理器

我一开始使用 packer 来同时使用 pacman 和安装 AUR 软件包。但是在我了解到其软件安装过程有 诸多安全隐患 后,我开始改用 trizenpacaur 是另一个较为稳妥的选择,而且在 reddit 上有一个机器人会在所有提到 yaourt 的帖子下面安利 pacaur ): trizen 会提示用户在安装前检查 PKGBUILD*.install 以及其他代码,而且 trizen 是用 Perl 而不是 Bash 写的。想要安装 trizen ,先根据 AUR 页面 通过 pacman 安装 trizen 所依赖的软件包,然后克隆其 git 仓库 到本地。进入包含 PKGBUILD 的文件夹并运行:

$ makepkg

来编译软件包,

$ pacman -U trizen-*.pkg.tzr.xz

来安装 trizen.

常用软件包

在设置完软件包管理器后,就可以大肆安装各种软件了!我的一些必备软件包括 emacs (在服务器上我只安装了命令行版本, emacs-nox), tmux (可以使用同一个命令行窗口来同时运行多个指令,非常有用), zshvim (作快速编辑之用)。

安全相关

Arch Linux 安装完成之后,我在把网站搬进去之前进行了一些安全方面的设置。

使用 ssh 安全登录

在本地机器上生成 ssh 密匙:

$ ssh-keygen -t rsa

把 ssh 密匙发送到服务器:

$ ssh-copy-id <username>@<server>

接下来再服务器上编辑 /etc/ssh/sshd_config

PermitRootLogin no
ChallengeResponseAuthentication no
PasswordAuthentication no
UsePAM no
AllowUsers <username>

这些改动会禁止 root 账户登录,禁止使用密码登录,并只允许特定用户通过 ssh 登录。

除此之外,把用于 ssh 的端口(默认为 22)改掉也是一个很棒的安全措施。继续编辑同一个文件(请记牢所选择的端口):

port <non-std-port>

为了让这些改动生效,重启 ssh 进程:

$ sudo systemctl restart sshd.service

接下来保留目前的 ssh 链接不变并在一个新窗口内尝试建立新链接以确认一切正常(保留原有链接以防设置出错):

$ ssh -p <non-std-port> <username>@<server>

防火墙设置

ufw 作为防火墙非常方便易用。使用 trizen 来安装 ufw 并开放允许连接的端口:

$ trizen -S ufw
$ sudo ufw allow <port>/<protocol>

如果想要允许 ssh 链接,开放 22/tcpssh (如果你改掉了默认端口,开放 <non-std-port>/tcp )。其他一些常用的端口有:

Port Usage
80/tcp http
443/tcp https
143 imap 通信
993 imap ssl 通信
25 收取外界来的邮件
587 smtp 通信 (不论有无 ssl

回顾已开放的端口并开启防火墙:

$ sudo ufw show added
$ sudo ufw enable

设置自动启动:

$ sudo systemctl enable ufw.service

同步服务器时间

使用 ntp 同步服务器时间:

$ trizen -S ntp
$ sudo systemctl enable ntpd.service

检查时间服务器的状态:

$ ntpq -p

设置 PTR 记录

DigitalOcean 会自动设置 PTR 记录,我唯一需要做的就是将水滴的名字改为绝对领域名称( FQDN ,帅气但是八成是机翻的译名取自 Wikipedia ),也就是 shimmy1996.com 。完成这一设置后,我可以通过以下命令来查看设置是否成功。

$ dig -x <ip_address>

正式启动服务器

在完成以上设置后,就可以为服务器托管网站做准备了。

建立网页文件夹

创建一个网页文件夹来放网页文件,一个比较普遍的选择是:

$ mkdir ~/public_html

确认该文件夹(以及用户的 home 文件夹)有合适的权限设置。权限设置可以用 chmod 修改(一般设成 755 就好)。可以在网页文件夹中放一个简单的 index.html 来方便测试。

安装 nginx

trizen 安装 nginx ,并编辑 /etc/nginx/nginx.conf 来设立 http 服务器(带有 listen 80 default_server 设置的部分):

server_name www.<domainname> <domainname>
root /path/to/public_html

server_name 这一行可以多列一些网址。如果你想一并架设邮箱服务器的话,一并将邮箱服务器地址列入网址就免去了生成额外的 ssl 证书的麻烦。在这些设置完成后,(重新)开始 nginx 并将其设为开机启动:

$ sudo systemctl restart nginx.service
$ sudo systemctl enable nginx.service

DNS 设置

下一步是为服务器完成 DNS 记录的设置。一开始必须设置的记录有三种: NSA ,和 CNAME 。我记下了一些比较常用的记录:

记录种类 主机名 数值 用法
NS @ DNS 服务器的地址 确认用于解析域名的服务器
A @ 水滴的 IPv4 地址 将主机名重定向到 IP 地址
CNAME www (可以是任何东西) @ www.<hostname> 设为主机名的
MX @ 邮箱服务器地址 指定邮箱服务器
CAA @ 标明 SSL 证书的授权机构 阻止其他授权机构为本站发行 SSL 证书

我的域名托管在 Google Domains ,但我的网站用的是 DigitalOcean 的 DNS ,所以我需要在 DigitalOcean 上完成设置并在 Google Domains 里加入 NS 记录。

在完成这些设置后,我就可以通过我的域名访问所架设的网站了,不过 DNS 记录通常需要数小时才会完全生效。

SSL 证书

Let's Encrypt 是个非常棒的项目。使用 certbot 这个工具就可以很方便的生成 SSL 证书。这里向 EFF 和 Linux 基金会的人们致以谢意。生成证书只需要运行 EFF 网站 上所记载的命令即可:

$ sudo pacman -S certbot-nginx
$ sudo certbot --nginx

为了给证书增加一点可信度,我还在 DNS 记录中加了一条 CAA 记录,标明 letsencrypt.org 是唯一允许给本站 SSL 证书授权的机构。目前 Let's Encrypt 还不支持通配符证书,不过会在 2018 年 1 月 添加这一支持。由于没有通配符证书,我只好在 nginx.config 里加上所有二级域名(这样生成证书的才能够为这些域名提供验证)。

下一步?

在鼓捣了几个小时后(其实大部分时间是在等 DNS 记录扩散),我的新站就上线了。既然选择了运行 VPS,我打算好好发挥它的潜能并架设了自己的电子邮箱。我正在考虑把架设邮箱过程中从各个网站七拼八凑其来的命令行笔记也整理成一篇日志。目前我仍在试图寻找使用 org-modehugo 里写多语言日志的最优工作流程。当我确信已经找到一套可以接受的解决方案的时候我会一并写成日志。

是 Spam 还是 Ham

遵循之前的计划,我打算将设置邮箱的过程记录下来。设置邮箱大部分地方都有教程,不过我需要添加不少额外的安全设置来避免邮件被扔进垃圾箱。

搭建邮件服务器

我八成是写不出比 这篇教程 更好的步骤说明的,所以我就在这里把我额外需要的一些设置记录下来。

设置 DNS 记录

在开始搭建邮箱之前,我需要设置 DNS 记录。我为我的邮件服务器地址设置了一条 A 记录,并用一条 MX 记录来标明所使用的邮件服务器。

创建 Maildir

在设置好 postfix 之后,我需要手动创建 Maildir 文件夹并赋予其合适的权限:

$ mkdir -p /home/<username>/Maildir/{cur,new,tmp}
$ chown <username> /home/<username>/Maildir/{,cur,new,tmp}
$ chmod 0755 /home/<username>/Maildir/{,cur,new,tmp}

SSL 证书

我没有使用 dovecot 自带的证书生成器,而是直接沿用了我网站的 SSL 证书。我将邮件服务器地址加入 /etc/nginx/nginx.conf 中的 server_name 下,并用 certbot 生成了合适的证书。在这之后,我修改了 dovecot 的设置文件 /etc/dovecot/conf.d/10-ssl.conf

use_ssl = yes
ssl_cert = </path/to/fullchain.pem
ssl_key = </path/to/privkey.pem

我也在 postfix 上用了这个证书。需要注意的是 dovecotpostfix 都需要用 root 账户运行才会有权限读取证书。

邮件客户端

我使用 Thunderbird 作为邮件客户端。收取邮件时,我使用 SSL/TLS,而发送邮件则使用 STARTTLS。

安全措施

设置好邮件服务器后,我试着发了几封邮件,不过发现都被 gmail 扔进了垃圾箱。似乎 gmail 最近添加了显示邮件安全检查状态的功能(在 gmail 中点击“查看原件”即可看到)。这些检查包括 SPF , DKIM ,和 DMARC 。由于我的邮件服务器没有通过最基本的 SPF 检查,所以我的头像显示为一个标着问号的八边形。为了避免邮件被扔进垃圾箱,我进行了一系列安全设置以保证我的邮件服务器能通过网上邮箱安全测试平台(我使用的是 intodnsmxtoolbox )的考验。

发件人策略框架( SPF )

SPF TXT 记录标明了某一域名所承认的邮件服务器地址。在我的情况下,我只会用到 MX TXT 记录中所提到的邮件服务器,所以我的 SPF TXT 记录就是:

v=spf1 mx -all

域名密匙邮件认证( DKIM )

我使用 opendkim 来为邮件署名,以验证邮件的确来自于我的服务器。在安装了 opendkim 软件包后,我遵循 Arch Wiki 里的步骤完成了设置。首先,复制设置文件模板 /etc/opendkim/opendkim.conf.sample/etc/opendkim/opendkim.conf 并编辑(端口可以随意选择):

Domain                  <domainname>
KeyFile                 /path/to/keys.private
Selector                <myselector>
Socket                  inet:<dkimsocket>@localhost
UserID                  opendkim
Canonicalization        relaxed/simple

接下来,在设置文件所指定的密匙文件路径下(默认为 /var/db/dkim/ ),生成密匙:

$ opendkim-genkey -r -s <myselector> -d <domainname> --bits=2048

执行指令后生成的不仅仅是 .private 密匙文件,还有装有完成 DKIM 设置所需 TXT 记录的 .txt 文件。这一记录的功能在于公布邮箱服务器的公共密匙。需要注意的是这条 TXT 记录有可能会被分成数条字符串,以满足每条字符串最长 255 字符的要求。为了查看 TXT 记录是否有设置成功,我运行了(需要安装 dnsutils 软件包):

$ host -t TXT <myselector>._domainkey.<domainname>

接下,重启 opendkim 服务并确保 postfix 在发出邮件之前执行加密。编辑 /etc/postfix/main.cf

non_smtpd_milters=inet:127.0.0.1:<dkimsocket>
smtpd_milters=inet:127.0.0.1:<dkimsocket>

在重启 postfix 后, DKIM 就开始运作了。

基于域名的邮件认证,报告和一致性检查( DMARC )

毫无意外,有一个软件包 opendmarc 可以用于部署 DMARC ,并且这一软件包也有对应的 Arch Wiki 页面。需要注意的是, DMARC 必须在 SPF 和 DKIM 都设置完成后才能生效。在安装软件包后,编辑 /etc/opendmarc/opendmarc.conf:

Socket inet:<dmarcsocket>@localhost

在启动 opendmarc 服务后,在 postfix 中启用 DMARC 邮件滤网(与 DKIM 滤网用逗号隔开):

non_smtpd_milters=inet:127.0.0.1:<dkimsocket>, inet:127.0.0.1:<dmarcsocket>
smtpd_milters=inet:127.0.0.1:<dkimsocket>, inet:127.0.0.1:<dmarcsocket>

最后,按照 Arch Wiki 所指示的步骤在 DNS 设置中加上一条 DMARC TXT 记录并重启 postfix 就大功告成了。

通过所有测试

check-auth@verifier.port25.com 发送测试邮件后,我收到了一份邮件服务器的测试报告。报告显示所有安全设置都在正常运作。除此之外, gmail 不再将我的邮件扔进垃圾箱了,而“查看原件”页面下也显示我的邮件通过了 SPF , DKIM , 和 DMARC 检查。 由于启用了 DMARC , gmail 还会每天向我的邮箱发送一份安全报告。折腾到这个地步后,我对我的新邮箱比较满意了,并准备废除我之前所使用的邮箱。我还在寻找可以自己架设的日历服务,希望不久的将来我可以完全摆脱在通讯方面对 Google 服务的依赖。

不再使用 Disqus

不久之前, Disqus 发生了一起 用户信息泄露事件 。这导致我开始重新考虑评论系统的选择:既然已经架设了自己的博客和电子邮件,也不差一个评论系统。

好家伙,坏家伙,丑家伙

我对 Disqus 将不同网站的评论统一成一个社交网络的主意抱有比较复杂的看法。我个人使用社交媒体时更多的是作为 “媒体” 而不是社交的工具:这些服务显然不适合发表长篇大论(所以大多社交网站帖子都充斥着链接和长图),而就算是作为发表随感的工具,我也觉得在这些网站上编辑文字不怎么理想(尤其是在手机上)。常年潜水的习惯使得我时常反过来审视自己的社交网站人格:我站在第三者的角度会怎么看这堆转推和赞所构成的怪物。

博客评论则比较不同。我在评论博客时更为放松:这种感觉更接近与博主一对一对话,而不是向整个网络广播自己的座标。社交媒体化的博客评论就不再给我这种感觉。使用 Disqus 的一大潜在好处大概在于能够吸引更多访客,不过我并不想让自己的博客评论区沦为又一个社交网络时间线:高价值的评论并不会因为我的网站不使用 Disqus 而消失(虽然相反的事情时有发生,并不是所有人都会愿意为了评论而注册新的社交网络帐号的)。

接下来就要说到 Disqus 比较丑陋的一面了。且不提在网站上嵌入我自己没有办法控制的 JavaScript 是一大安全隐患,我直到昨天才意识到 Disqus 的访客数据收集是默认启用的。由于我不打算通过博客获得收入,以牺牲访客隐私为代价换取 Disqus 的服务并不值得。除此之外,我还发现 Disqus 评论中的大部分“赞同”都来自于挂着交友网站的僵尸帐号。至于这些僵尸帐号的来源是被盗用的帐号还是水军机器人我就无从了解了。总之我可不想让这些僵尸帐号在我的博客上晃悠。

寻找替代品

我决定自己架设评论系统并尽量避开任何第三方服务。在细心搜寻后,issostaticman 成为了最终的候选者。 Isso 是一个使用 Python 写成的轻量评论服务器;而 staticman 则是一套将评论转换成文本文件并自动加入博客 Github 仓库的 API 。安装 isso 意味着我必须使用我之前一直尽力避免的数据库;使用 staticman 则可以让我的网站保持静态,但是必须依靠 Github 的 API (如果我不自己架设 staticman 的话,还需要 staticman.net 的官方 API )。虽然保持一个完全静态的站点很吸引人,不过我还是决定先尝试 isso ,看看脱离第三方服务是否值得我花时间鼓捣数据库。

我在寻找评论系统的过程中还发现了一个有趣的替代品:Echochamber.js

设置 isso

Isso 的官网有很详细的 说明文档 。我从 AUR 安装了 isso 并使用 systemctl 启用了它。设置过程出奇的顺利(包括数据库的部分),因为我的 isso 和博客共用一台服务器,我使用了与默认不同的 设置 。我所遇到的唯一问题在于 smtp 。在检查 postfix 的运行状态后,我很快发现问题在于 smtpd_helo_restrictions :在停用 reject_unknown_helo_hostname 后, isso 就能使用 smtp 发送通知邮件了。除此之外,我稍微花了点时间修改 isso 的 CSS 模板。新的评论区看起来不仅更契合博客主题,速度也比 Disqus 快多了。

祝评论愉快!

回顾 2017

2017 年再过几个小时就结束了,所以我觉得很有必要回顾一下过去这一年。但愿我在写完这篇日志的时候还能觉得 2017 过得没有后悔。

我都做了啥

我从六月份开始全职工作了。社畜生活其实比我想象的要轻松不少,我的日常生活比上学时反而有规律得多:至少 4 小时的睡眠时间不再显得那么奢侈,而且我总算能分配一部分时间来发展兴趣了。

在 2017 年里:

  • 使用 Emacs 三个月。
  • 使用自己架设的电子邮箱三个月。
  • 架设了新的站点并且更新了比 2015-2016 两年更多的内容。
  • 发现自己其实有点煮饭的隐藏才能
  • 我在后六个月中保持几乎每天跑步。我在 2 小时之内完成了我的第一个半程马拉松比赛。
  • 由于跑步,我的体重下降了 10 千克左右。

我觉得 2017 是很充实很开心的一年。

跟住去边度

最近常常听黄子华的栋笃笑,而 跟住去边度 给我留下的印象最深。我也打算问问自己这个问题。 2018 我会:

  • 以马拉松为目标继续训练,有机会的话完成一次正式比赛。
  • 写 20 篇以上的日志。
  • 获得第一个 PGP 密匙签名。
  • 安装 Gentoo 。
  • 少看,多阅读。

如果我有从过去那些我制定后没能执行的计划里得到任何经验的话,那就是定计划时最好稍微低估自己的能力,所以我的新年目标就先列到这里。在踏入 2018 后我会视情况添加新的内容。

新年快乐!希望 2018 也会是充满惊喜的一年!

自己画头像

我使用星球大战中旧共和国的标志作为头像已经有不短的时间了。不过最近,当我试图统一我所有的“社交网络人格”时,我意识到独特的头像往往是最为直接的在网上认人的方式(这大概就是为何 Gravatar 这类服务 如此受欢迎 会存在)。这么一想,拿 Wookiepedia 上的图片直接作为头像不是什么明智的行为。于是我决定:自己画头像!

由于我并不觉得自己有多少艺术细胞,我最初尝试的方法是在 GeoGebra 里用尺规作图复制原来的头像。这种作图方式很是让人上瘾,但遗憾的是:在荒废几个小时后,我得到的只是一堆纠缠不清的曲线。

GeoGebra 中的诸多失败作之一。

事已至此,我开始意识到我是画不出像旧共和国标志的那样复杂的头像的,所以我采取了另外一种策略:从这些失败作中抽取一个更加简练的图样。

我逐渐简化头像的过程。

我把原图里六芒星升起的部分提取出来,并舍去了碍事的翅膀形部分使得星形能够居中。经过少许修改后更接近流星的图样看起来(至少对我来说)非常赞。在短短几分钟后,我就完成了我的头像设计。我保留了旧头像的暗红的配色(实际用的是 #700000 而不是原图的 710100 ,因为我有个位数字强迫症)并加上了灰色的背景( #707070 ,白色背景有点太刺眼了)。

我推特资料上的完成版头像。

我还尝试了其他不同的配色,比如反色版本,以后可能会拿来作为我其他项目的图标。我所有还活跃的社交网站都已经换上了新头像,包括网站图标。这下大家应该可以更容易地在不同网站上认出我了 XD。

Mastodon 尝鲜

我在 上一篇日志 里提到过,我并不习惯于在社交网络上发帖子。不过不久之前,我偶然撞见了一个很久没有听到过的词:微型博客。不少社交网络站点,例如 Twitter ,本质上还是一个微型博客服务。这种定义下的 Twitter 对我更加具有吸引力:我可以把一些随想,趣事和生活中其他不大适合写进博客的点点滴滴塞进去。但即使如此,我还是发推有一种“向整个互联网发送座标”的感觉。嗯,那么只好自己搭建一个微型博客了。

Mastodon 就是一个很好的解决方案。对与在最大化网络人格和最小化个人信息泄露之间进退两难的我来说,存储去中心化、但实例之间又紧密相联的 Mastodon 非常理想。如果人们愿意为了好看的头像将个人信息拱手送出的话,搭建一个 Mastodon 实例可以算得上是一个划算的多的买卖。

在 Arch Linux 上安装 Mastodon

我在一番搜寻后,居然没有找到一篇专门针对 Arch Linux 的 Mastodon 安装指南,这有点让我惊讶。不过得益于丰富的软件包,在 Arch Linux 上安装 Mastodon 其实比在 Ubuntu 上更加简单。 官方指南 上有很详尽的步骤说明,我就简单补充一些只适用于 Arch Linux 的部分。

软件包依赖

我把所有依赖以及相对应的 Arch Linux 软件包都列了出来。完全没有手动克隆 git 仓库的必要。 npm 会在安装过程中用到,但没有在官方指南中列出。

依赖 软件包
node.js 6.x nodejs-lts-boron
yarn yarn
imagemagick imagemagick
ffmpeg ffmpeg
libprotobufprotobuf-compiler protobuf
nginx nginx
redis redis
postgresql postgresql
nodejs nodejs
rbenv rbenv
ruby-build ruby-build
npm npm

在安装 rbenv 后,我需要把 eval "$(rbenv init -)"= 加入 =.bashrc.zshrc 中(安装脚本也会提示这一步骤)。

Mastodon

创建用户 mastodon 并用 visudo 把该用户加入 sudoers

useradd -m -G wheel -s /bin/bash mastodon

接下来就可以克隆 Mastodon 的 git 仓库并开始 安装 node.js 和 ruby 的依赖 了。在这一过程中会用到 npm 。我在运行 yarn 时,遇到了一个 ENONT 错误:无法找到 ./.config/yarn/global/.yarnclean 。手动创建了迷失的文件解决了这个错误。

PostgreSQL

除了安装 postgresql 软件包外, 我遵循 Arch Wiki 里的步骤初始化了数据库集群:

$ sudo su postgres
[postgres]$ initdb --locale $LANG -E UTF8 -D '/var/lib/postgres/data'

在开始并启用 postgresql.service 后,我就可以以用户 postgres 的身份登录 psql 命令行并给 Mastodon 建立用户了(可以使用 psql 命令 \du 来确认用户列表):

$ sudo su postgres
[postgres]$ psql
[psql]# CREATE USER mastodon CREATEDB;
[psql]# \q

端口设置可以在 postgresql.service 里找到,这会在编辑 .env.porduction 时用到。

Redis

postgresql 差不多,我安装了 redis ,开始/启用了 redis.service 。端口选择和允许连接的地址都可以在 /etc/redis.conf 里设置。

Nginx 和 Let's Encrypt

官方指南已经提供了很详尽的步骤,这里不再赘述。

.env.production

照配置文件里的说明做就可以了。我唯一弄错的地方是连接 postgresql 所需的 DB_HOST 。在查看 postgresql.service 的状态后,我找到了正确的路径, /run/postgresql

计划进程和缓存清理

照官方指南做就好。我安装了 cronie 来安排 cron 作业。

使用感受

网页版界面很不错,我很喜欢可以一边刷时间线一边慢慢写嘟文这一点(而不是在被迫停留在页面顶端)。我在尝试了数个 Mastodon 手机客户端后选定了 Pixiv 开发的 Pawoo 。到目前为止, Mastodon 给我的感觉是一个比 Twitter 更加舒适、更能激发我写东西的平台。我试着推动自己每隔几天就写一条嘟文。虽然目前为止我写的大都是跑步的记录,但我会渐渐丰富我的嘟文内容的。

我很希望看到 Mastodon 对多语言嘟文提供支持。目前我用的办法是给中文和英文的嘟文打上不同的标签,但这么做不仅使嘟文更加臃肿,也使得我的时间线对大部分人来说可读性只有 50% 。可惜的是,目前的诸多社交网络里只看到 Facebook 对此提供了支持。

在网站页脚,我已经把 Twitter 换成了我的 Mastodon 页面 ,随时欢迎各位来访。

我的键盘 2018 版

为了完成主页施工计划上的最后一条项目,我重新浏览了旧博客里关于键盘的日志并决定翻新这些文章,同时加入一些近期的新尝试。

入门

我在 2014 年入手了第一块机械键盘,使用 Cherry MX 青轴的 WASD v2 104 键键盘。我选了 WASD 的主要原因是他们键盘较为简约的外形和客制化键帽的服务。我在 2014 年还入手了第一块 60% 键盘,使用 Cherry MX 茶轴的 Poker II 。在那时候可能由于 Cherry 的专利尚未过期,所以键盘轴的选择要比现在少得多。当然如果不考虑 Cherry MX 兼容性,替代品还是有的( Matias , Topre , IBM 弹簧轴等),但入手更加困难。

我最初的主力是一块我七拼八凑起来的基于 GH60 的 60% 键盘。我使用的键盘轴是改装了 62 克弹簧的 Cherry MX 白轴( ErgoClear ),这更多的只是想尝试键盘轴改装而不是因为偏好。除此之外,我发觉自己比之前用 Poker II 的时候更经常修改键盘布局了。虽然 Poker II 自带的宏编辑功能听上去很棒,但复杂的步骤使得我从来没有在不看说明书的情况下成功完成过编辑。而就算我废了老大力气完成了宏的设定,我过一段时间就会把宏的存在抛在脑后。相比之下,编辑 GH60 的固件后,至少我还能查看设定文件来回忆自己的设定。我早期修改键盘布局的尝试并不太成功:在我看来, 60% 键盘的键位布局太标准了,以至于(在保持 QWERTY 布局下)任何大范围修改都会让人觉得别扭。举个例子:我完全没法找到第二个适合回车键的位置。我所作的布局修改大多只是数字小键盘和功能键的映射以及交换大写锁定和控制键,完全没发挥出 GH60 的潜能,充其量只不过和使用了 xkb 的普通键盘旗鼓相当。

顺便一提,我曾经想过要收集所有键数布局的键盘,但很快的发现这是一个不切实际且烧钱的想法。目前为止在常见的键数布局中,我尝试过 104 键, 96 键, 87 键, 75 键, 60 键,和 40 键键盘。这当中的绝大多数对我来说在体验上并没有太大区别,除了 60% 或 40% :要想把所有标准键放上去是需要动一番脑筋的。

ErgoDox 和 Planck

ErgoDox 是第一个促使我真正下心思选择键盘布局的键盘。正是由于布局和传统键盘相差甚远, Ergodox 在键位布局选择上提供了很高的自由度:我一眼就能找到七个适合回车键的位置(传统右侧小拇指位,拇指区的四个 2u 键位,以及中心偏下的两个 1.5u 键位)。从 2015 开始,我就几乎只使用 ErgoDox 了。 ErgoDox 的好处在我开始使用 Emacs 后更加明显:能够轻而易举地够到控制键和转换键的感觉非常棒。

我的 ErgoDox 基本层布局

ErgoDox 还有很多潜力没有被我发掘出来。如你所见,我还没有想出拇指区部分键位的最佳用处。目前除了基本层外,我额外设置了三层键位布局:一层用于功能键,一层用于数字小键盘,最后一层是经过修改的 Dvorak 布局。我还没有在 Dvorak 层上花太多时间,不过我对 Dvorak 减少手指移动次数的功效很有兴趣。说到人体工学, ErgoDox 设计有个额外的好处:我书桌的正中央终于可以从键盘的统治下空出来了,就算没有一张超级深的桌子我也可以不受键盘干扰正常看书。

我的 ErgoDox Dvorak 层布局

Planck 是另一块让我下心思设计布局的键盘。 40% 键盘所能塞下来的东西其实多的让人吃惊。但是使用 Planck 时的舒适性不可避免地被它的尺寸所妨碍了 - 相比之下,使用 ErgoDox 这种分体键盘时两手可以保持更为自然的姿势,而不是以奇怪的角度挤在一起。我觉得 Let's Split - 基本上就是分体版的 Planck - 会是个不错的选择。

我的 Planck 布局

键帽狂热期

在我发现了 Geekhack 论坛后,我在很长一段时间里都会疯狂刷新团购和兴趣调查版,以收集其他用户所设计的客制键帽情报。我发现自己的兴趣逐渐地从色彩对比强烈的配色转向了更为统一,柔和的设计。在键帽形状的选择上,我也偏好没有高低梯度的类型,比如 DSA 。键帽图样上我更喜欢文字而非图案,有意思的是我并不觉得空白键帽有多么值得欣赏。这些癖好使得我的寻找键帽之旅异常困难:要想给 ErgoDox 配齐一整套图样相称的键帽可不是什么容易的事( Planck 因为全是 1u 键,所以要容易得多)。

设计自己的键盘/布局

我有时会冒出设计自己的键盘的念头。 ErgoDox 已经很接近我理想中的键盘了,但是它还 是有点笨重,而且拇指区边缘的键比较难按到。我原先一直在 Emacs 里使用 C-HomeC-End 来移动光标到文件开头/结尾,这两个键位组合使我不得不尽力伸展大拇指,导致 关节有些酸痛(直到我发现 M-<M-> 才是正确的打开方式)。一个更加小巧,拇指区键位更加紧凑的 ErgoDox 应该就是我眼中完美的键盘了。对了,虽然我以前从来没有觉得无线键盘有多么必要,但因为 ErgoDox 的分体式设计,如果它有无线版本,我就可以像使用任天堂 Switch 那样躺在床上打字了。

自从我开始使用 Emacs 作为主力文本编辑器,我就一直在使用 keyfreq 来记录每个键/组合键的使用频率。在我收集了足够多的数据后,我会以此为根据来调整我的键盘布局。

键盘像素画

我之前跟风 Geekhack 众,也给我的键盘画了像素画作为签名。

我的键盘像素画 I
我的键盘像素画 II

给键盘画像素画其实挺有意思,要想保持精确的比例几乎是不可能的,这就需要在精准和简约之间作微妙的平衡。我有时间时会继续更新这些像素画的。

施工完成

历时八个月,我的博客终于到达了我觉得可以摘掉施工警告的程度。不过我并没有删除原先的站点施工计划,只不过把它移到了这篇日志里。

施工计划

  • 找一家新的服务器提供商 目前使用 DigitalOcean 。
  • ☑ 在服务器上安装 Arch Linux 。
  • 搜寻 WP 的替代品。 Hugo 很不错。
  • 找一个合适的主题。 目前使用 hugo-xmin ,考虑 fork 出来写成自己的主题( soresu )。
  • ☑ 完成服务器端设置,比如添加 post-receive 来实现 git 自动部署。
  • ☑ 可以切换 当前页面 语言版本的语言切换按钮。
  • ☑ Disqus 支持。
  • ☑ 用 MathJax KaTeX 实现 \(\LaTeX\) 表达式支持。
  • ☑ 把导航页的内容搬过来并翻译。
  • ☑ https 支持。
  • ☑ 备份原 WP 站点。
  • ☑ 转移域名到 Google Domains ,并完成 DNS 设置。
  • ☑ 尝试使用 org-mode 或者 R markdown 来写博客。
  • ☑ 解决 emacs 不兼容 fcitx 的问题。
  • ☑ 设置多语言支持,添加合适的翻译字符串。
  • ☑ 使用 Google 的 Noto Sans 字体(拉丁字母使用 Oxygen Sans ),代码则使用 Source Code Pro Iosevka 。
  • ☑ 为站点和社交网站找一个合适的图标/头像。
  • ☑ 改善文章页面模板使其显示标签和分类。
  • ☑ 改善网站外观,比如隐藏超链接的下划线等。
  • ☑ 架设自己的邮箱。
  • ☑ 解决 org-modehugo 略不兼容的地方,比如代码高亮。
  • ☑ 尝试把 hugo new 变得更有用一些,比如直接创建多语言版本等。
  • ☑ 抛弃 Disqus 自己搭建评论系统。
  • ☑ 使用 Let's Encrypt 的通配符证书。
  • ☑ 把比较有价值的旧文章搬过来。

现在主页上是啥?

大部分我觉得别人会感兴趣的有关我的信息都可以在关于或联系方式页面里找到,所以对于主页应该放些什么,我实在没啥好主意。由于我感觉之前的站点施工计划是个提醒自己的不错方式,我会用另外一个任务清单来取代以完成的施工计划:我在 2018 年想实现的目标。我绝对不是那种最有干劲的人,但每每看到一张未完成的任务清单,我的强迫症神经还是会跳一跳的。那么,就让我试试看这么做效果如何吧。