何も考えずにdolphinサーバーを建ててみる

ふと何も考えずにサーバー(インスタンス)を建てたくなることってありますよね

## はじめに

インフラに関しては何も考えていないため、見るに堪えない場合はそっ閉じしてくださるとありがたいです。
あとすべて終わった後にこの記事を書いているため、スクショなどは無いです
(そもそも公開しようと思っていなかったため)

## 前提条件

今回建てるdolphinサーバーは、めいめい氏のフォークのめいどるふぃんを使っています
https://github.com/mei23/dolphin

ドメインとしては、`dolphin.sharkman.hoge`で公開するものとします
(架空のドメインのはず)

作業用の端末として、SSH接続できるLinuxを想定しています。
WindowsでもTera termでの接続も頑張ればできるのかもしれませんが、個人的にTera Term経由は結構問題が起こる印象のためオススメしません
ただそのためにLinuxを調達するのはかなり面倒だと思うので、筆者のWindows環境としてはVMWareで仮想PCを作成→適当なLinuxをインストールして、その仮想PCからSSH接続をしてアクセスする形をとっています
正直適当なLinux環境ができるのであれば多分WSLとかでも全然問題ないはず…

## どこのVPSを使うのか

今までは脳死でLinodeやVultrとかって言っていたんですが、気づいたらかなりVPSが増えている状況になりました
今は円安とかもあるので、そこら辺の部分も考慮して選ばなくてはなりません
VPSの比較については以下のサイトが一番です。Googleで上位にヒットするブログ記事は海外VPSのことに1ミリも触れておらず、国内で比較してconoHaが一番!とか言っててほとんど参考にならんので…(conoHa自体はたしかに悪くはないと思うのですが、LinodeやVultrとかWebARENA Indigoとかと比べると、どうしてもコストでの魅力はあまり…)
https://vpshikaku.com/

色々悩んだのですが、自鯖のmisskeyでも使っていて、$5でそれなりのスペックを建てることが可能であるLinodeの1GBプランで建てることにしました
初めて建てる場合はコストを切り詰めようと考えずに、conoHaとかを選んだほうが良いと思います

## 参考記事

- めいどるふぃん公式セットアップ手順

https://github.com/mei23/memo/blob/master/misskey/Setup-Ubuntu1804-Dolphin.md

- のえる氏の Misskeyのサーバを設置する（v11系）

https://blog.noellabo.jp/entry/2019/08/14/8i3RHuZ1wJNDinIn

- Oracle Cloud Always Free で建てた先駆者 (xianon氏)

https://qiita.com/xianon/items/7ed6d52ff3b64f5fb26a

## 下準備

### 適当にVPSを借りる

Linodeのアカウントを用意して、左のメニューから`Linodes`を選択し、`Create Linode`を押下します

今回は以下のスペックで借りました
```
Choose a Distribution: Ubuntu 22.0.4 LTS
Region: Tokyo,JP
Linode Plan: Shared CPU → Nanode 1 GB
Linode Lable: (自動生成された名前)

あとは未設定です
```

### SSH接続できるようにするまで

鯖を作ったらSSH接続できるための下準備です。コンソールで繋ぐ前にSSHの鍵を作る作業をしましょう

作業用端末のコンソールで`ssh-key`を入力すると、SSHの鍵が生成されます(生成時にどこのファイルに保存するのかを聞かれるため、複数のサーバーでSSH接続している/予定がある場合はフォルダを分けておくと後々管理が楽です)

成功すると指定したファイルの中に`id_rsa`と`id_rsa.pub`というファイルができているはずです

次に、お好みのエディタで`.ssh/config`を記述します

```
Host dolphin
    User ${任意のユーザー名}
    Port 22  //(任意のポートで構いませんが、このあとのsshdの編集でここの値は合わせてください)
    HostName <鯖のIPアドレス>
    IdentityFile <秘密鍵のファイルパス>  //例:~/.ssh/id_rsa 
```

Linodeでは、作り立ての鯖はrootユーザーしか作成されていないため、とりあえずrootユーザーで入ったあと、sudo権限を持ったユーザー(管理者ユーザー)を作ります

鯖にアクセスする方法はたくさんあると思いますが、今回はLinodeが提示しているアクセス方法そのまま使います

```
ssh root@<鯖のIPアドレス>
```

次回以降接続するための管理者ユーザーを作成します。今回はubuntuで建てているので、adduserコマンドの力にお任せします(表記が連続するため、以降 ${任意のユーザー名} のところは hoge に仮置きします。適宜置き換えてください)

```
adduser ${任意のユーザー名}
```

作成するユーザーのパスワードの入力を求められますので適宜入力してください。その後のユーザーの情報を入力するところは空白で問題ありません

ユーザーが作成されたら次のコマンドを叩きます
```
gpasswd -a hoge sudo
```

これで管理者ユーザーができました。次に作った公開鍵をサーバーに渡す作業をします
ここでは力技で、「サーバーに公開鍵のファイルを作成→編集をし、手元にある公開鍵の中身をコピペする」方法でいきます

まず新しく作成した管理者ユーザーに切り替えます(表記が連続するため、以降 ${任意のユーザー名} のところは hoge に仮置きします。適宜置き換えてください)

```
sudo su - hoge
(入力後、パスワードを求められます)
```

おそらくターミナルの表記が`hoge@localhost:~$`みたいに変わっていると思います
ホームディレクトリに居る状態ですので、そのまま以下のコマンドを入力します
```
mkdir .ssh
chmod 700 .ssh
cd .ssh
touch authorized_keys
chmod 600 authorized_keys
```

お好みのエディタでauthorized_keysを編集して、id_rsa.pubの中身をそのままコピーします(ここではvimを使うことを前提として記載します)

ターミナルを新規のウインドウで開いて、公開鍵があるディレクトリで`cat id_rsa.pub`を入力すると公開鍵の中身が出力されるので、それをコピーした後にSSH接続しているターミナルに戻って貼り付けると良いです

貼り付けたらsshdの設定をいじります

```
sudo vim /etc/ssh/sshd_config
```

- #がついている箇所はコメントアウトで無効になっています。変更する場合はコメントアウトを外してください
- 以下の設定はセキュリティの観点上、やっておくことを推奨します
    - ルートからのログインを禁止にする `PermitRootLogin no`
    - パスワードでのログインを禁止にする `PasswordAuthentication no`

以上、設定が完了したらsshdが正しく動くのかテストを実施します。
ここが間違っているとsshでの接続ができなくなるため、正しく動くかどうかチェックしてください

```
sudo sshd -t
```

問題なければ、sshdサービスを再起動します

```
sudo systemctl restart sshd
```

ファイアウォールを設定して、特定のポートの接続を許可します

```
sudo ufw allow 22/tcp
sudo ufw enable
```

22の部分は上記のsshd_configで設定したポートで記載します

ここまで正しく設定されていれば、次回以降`ssh dolphin`を入力すれば接続できるようになるはずです

接続が完了したらシステムのアップデートをかけます
```
sudo apt update
sudo apt upgrade
```

### スワップ領域を作る

dolphinはたしかにmisskeyより軽量ではありますが、正直1GBは割と足りない場合があります(自分も前に建てたときに失敗した)
スワップ領域を設定してあげることで、メモリ不足によるビルド失敗を防ぎます

```
sudo fallocate -l 2G /swapfile
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
```

上記のコマンドを打つと2GB分のスワップ領域が生成されます。
これだけでも良いのですが、再起動をするとこのスワップ領域は消えてしまうため、常に領域を確保してほしい場合は以下の作業を実施してください

`/etc/fstab` をエディタで開いて、以下の内容を記述します

```
/swapfile none swap sw 0 0
```

これで再起動後も領域を確保してくれるようになります

### ドメインの設定をする

ドメインのDNSレコードを設定します

|レコードのタイプ|名前|内容|
|:-:|:-:|:-:|
|A|dolphin|<鯖のIPv4アドレス>|
|AAAA|dolphin|<鯖のIPv6アドレス>|

## dolphinを入れていく

### 管理者ユーザーでの作業

#### 作業用ユーザーの作成

以下のコマンドを入力して作業用のユーザー`dolphin`を作成します
```
sudo adduser --disabled-password --disabled-login dolphin
```

#### Nodeのセットアップ～yarnのインストールまで

ここでは、nodeのバージョン管理ツールとして n を導入するところまで進めます

自分の環境下だと、めいどるふぃんのやり方でNodejsを入れることができなかったので以下の作業を実施しました

```
sudo apt install nodejs npm
```

npmが使えることを確認したら以下のコマンドを入力します

```
sudo npm install n -g
```

導入が成功したら、とりあえずnodeのltsのバージョンを落としてきます

```
sudo n lts
```

`node -v`で落としてきたバージョンと同じになっていれば成功です
上記の作業まで完了したらyarnをインストールします

```
sudo npm install -g yarn
```

#### パッケージをインストールする

以下のパッケージをインストールする
```
sudo apt -y install redis git build-essential nginx ssl-cert letsencrypt ffmpeg postgresql
```

#### DBロールとユーザーの作成

```
sudo -u postgres psql
```

を入力すると、postgresqlのコンソールにアクセスします

```
# ロールの作成と確認 (passwordは適切に置き換える)
create role dolphin LOGIN CREATEDB PASSWORD 'password';
\du

# DB (dolphin) の作成と確認
create database dolphin owner dolphin;
\l

# 接続終了
\q
```

作成が完了したら、とりあえずdolphin起動までの作業で管理者ユーザーで設定することは以上で完了です

### dolphinユーザーでの作業

```
sudo su - dolphin
```

を入力してdolphinに切り替えます

#### dolphinをインストールする

git経由でめいどるふぃんのソースコードを落としてきます

```
git clone https://github.com/mei23/dolphin.git
```

落としてきたら`cd dolphin`でカレントディレクトリを移動します
そこでセットアップのコンフィグを編集します
```
cp .config/example.yml .config/default.yml
vim .config/default.yml
```

編集が必要な個所を以下に提示します
```
# Your instance name
name: 'Dolphin'　　#サイトに表示される名前となります

# Final accessible URL seen by a user.
url: https://example.tld/  #公開するドメインに置き換えてください(httpsは付けた状態で)

# Listen port
port: 3000  #ポートをいじる必要がある場合、変更したら後述のnginxのポートも変更してください

db:
  host: localhost
  port: 5432

  # Database name
  db: dolphin

  # Auth
  user: dolphin
  pass: 設定したパスワード
```

オブジェクトストレージを利用する場合は、以下の設定も追加で編集してください。今回はCloudflare R2を利用したときの設定です
バケットの設定などは以下を参照してください

- hihumikan氏の記事

https://qiita.com/hihumikan/items/1f692f3bd5516820e0ec

- ぎんなん氏の記事

https://fullstuckengineer.com/2023/07/12/vpscloudflaredocker%E3%81%A7misskey%E3%82%B5%E3%83%BC%E3%83%90%E3%83%BC%E3%82%92%E7%AB%8B%E3%81%A6%E3%82%8B%EF%BC%88%E3%81%9D%E3%81%AE%EF%BC%93%EF%BC%89-%E3%82%AA%E3%83%96%E3%82%B8%E3%82%A7/

```
# こちらはコメントアウトしてください
#drive:
#  storage: 'fs'

# OR

drive:
  storage: 'minio'
  bucket: ${作ったバケット名}
  prefix: ${任意の文字列}　　#ここで決めた文字列のディレクトリの直下にファイルが格納されます
#デフォルトで用意されていないので、追加で記述してください
  baseUrl: SettingsにあるPublic Bucket URL もしくは バケットのカスタム ドメイン
  endpoint: SettingsにあるS3 API から、https:// と /<バケット名>は削除したもの
# 使わないため、コメントアウトのまま
#  port:
  useSSL: true
  accessKey: <取得したアクセスキー>
  secretKey: <取得したプライベートキー>
```

編集が完了したら、いよいよビルドです
そんなに気を引き締めず軽い気持ちでやっていきましょう

```
yarn install
# ビルド
NODE_ENV=production yarn build
# DBスキーマ作成
yarn migrate
# dolphin起動
yarn start
```

`yarn start`をしたとき、`Now listening on port 3000 on https://example.com`などが表示されたらビルドに問題が無い状態です

## 自動で起動できるようにする

### 証明書を取得する

この鯖自体はCloudflareのDNS通していますが、プロキシや証明書を通すと8割ぐらいの他鯖と通信ができなくなってしまいます
そのため、今回はシンプルにLet`s Encryptで証明書を取得することにしました

```
sudo certbot certonly -d <サーバーのドメイン> -m <連絡を飛ばしてほしいメールアドレス> --standalone --dry-run
# 問題無ければ--dry-runを外して実行
sudo certbot certonly -d <サーバーのドメイン> -m <連絡を飛ばしてほしいメールアドレス> --standalone
```

### nginxをいじる

ドキュメントでは直接sites-enabledにコピーをしていますが、本来であれば注釈で書いてある通り、sites-availableにコピーしてシンボリックリンクを貼るのがお作法的には良いです(動くには動きます)

```
sudo cp ~dolphin/dolphin/docs/examples/dolphin.nginx /etc/nginx/sites-enabled/
# 本当は sites-available にコピーして sites-enabled からシンボリックリンクが流儀
```

一応お作法に則った方法としては以下のような形(打ってないのでもしかしたら間違っているかもしれないです。詳しくは参考記事を見てください)

```
sudo cp ~dolphin/dolphin/docs/examples/dolphin.nginx /etc/nginx/sites-available/
cd /etc/nginx/sites-enabled
sudo ln -s ../sites-available/dolphin.nginx
```

設定ファイルのコピーが終わったら編集します

```
sudo vim /etc/nginx/sites-enabled/dolphin.nginx
# serverブロックの中にあるドメインを編集してください
# また、証明書の読み込み方のチェックは改めて実施してください
```

編集が終わったら`sudo service nginx reload`してnginxを再読み込みします

### systemdで起動させるようにする

ここで設定することはほぼ無いです
一連の作業を実行して問題無ければ大丈夫です

```
#serviceファイルのコピー
sudo cp ~dolphin/dolphin/docs/examples/dolphin.service /etc/systemd/system/
sudo systemctl daemon-reload
sudo systemctl enable dolphin
# サービス起動
sudo systemctl start dolphin
# 起動しているかどうかを確認する
sudo systemctl status dolphin
```

基本的にはここで問題が出ないとは思いますが、自分は何故かここのサービス起動で失敗してしまいました。
色々作業をして原因を調べたところ、ExecStartで設定されているパスが存在しないため、怒られている模様です

私は以下のように修正しましたが、もしかしたらいい方法があるかもしれないです
```
# 修正前
ExecStart=/usr/bin/npm start
# 修正後
ExecStart=/usr/local/lib/node_modules/yarn/bin/yarn start
```

サイトにアクセスして、投稿ができるか、ファイルのアップロードが正常にできるかどうかなどの動作確認を終えたら鯖建て完了です。お疲れさまでした

## 所感

dolphinそのものの情報自体は少ないですがmisskeyの派生が故、misskeyとしての情報を流用できる箇所が多いので鯖を建てること自体はそこまで難しくない印象です

鯖建て自体もナレッジの共有がだいぶ進んだこともあり、多分そこまで苦労することはないでしょう(起動まで1時間半程度かかった程度。多分ゲームしながらやってるからだとは思います)

オブジェクトストレージ周りは結構手こずりましたが、正直Pleromaで設定した時より情報がちゃんとあるだけ全然マシでした。

---
**ここからはdolphin自体の感想**

2019年はバリバリmisskeyにドップリ浸かっている時期でしたので、dolphin自体はリリース当初から知っていました。
ただ今居るインスタンスでそんなに苦労をしていなかったため、わざわざ鯖を建てようとは思っていませんでした。

dolphin自体はたしかに軽いのですが、元々2019年11月にリリースされてから開発が停滞していたもので、それをフォークという形でメンテナンスをしている現状、どうしてもMisskeyとは遅れというか追従はほぼ現実的ではありません。(2019年11月はMisskey v11が現役で、その3か月後にはv12がリリースされている状況でした)
時代背景的にmastodonほどではないにしろ、Misskey=結構重いみたいなところがあり低スペックで動かすのには荷が重く、おひとりさまや少人数インスタンスを運営する上ではここら辺がネックでした。当時はそういう謳い文句でmisskeyの差別化が図られたものの、色々リリースが繰り返されるうちに、最適化が進んで割と動かしやすくなった現況で、積極的にdolphinを使おうという酔狂な人は少ないのではないでしょうか。

gitのREADMEから分かるように、「おひとりさま」向けである以上、かなり機能が絞られている形です。またドライブも搭載されておらず、管理者としての設定もだいぶ簡略されています。

https://github.com/misskey-dev/dolphin

今回ではめいどるふぃんを利用しているため、GTLやリレーに対応していますが、元々がv11ベースとなっている以上、アンテナやチャンネル、クリップ機能などv12以降搭載されている機能は実装されていません。

https://github.com/mei23/dolphin

歴史的な背景的にも、doplhin自体は新型コロナウイルスが流行る前の、いわばレガシーな環境であった、現在2023年の9月に新しく動かすためにわざわざ建てるものでは無いということで、私がやっていること自体はただの趣味の一環で動かしている状態、いわばジャンクPCで戯れているのとほぼ同義なんだろうなと思っています。

そう考えると今回の記事っていったい誰得なんだというところですが、フォークという形で生き延びているものもあるという一例としては面白いのではないかな…と思っています。新規で建てるのであれば、正直misskey本家で良いと思います。メンテナンス的にも、情報量的にも。