listmonkは、Go製のバックエンドとVue製の管理画面を持つ、自己ホスト型のニュースレター・メーリングリスト管理ツールです。PostgreSQLをデータストアとして使い、単一バイナリまたはDockerで配信キャンペーンや購読者管理を行います。SMTP送信、バウンス処理、公開購読ページ、キャンペーンアーカイブなど一通りの機能をまとめて提供します。
cmd/配下のGoファイル(campaigns.go、subscribers.go、bounce.go、archive.goなど)がEcho製のHTTPハンドラとして、管理APIと公開APIの両方を担っています。内部にmanagerパッケージがあり、キャンペーン送信やバウンス受信Webhook(BounceWebhook)を処理し、設定はconfig.tomlまたはLISTMONK_*環境変数経由で読み込まれます。データはPostgreSQLに保存され、起動時に`--install`や`--upgrade`でスキーマを初期化・マイグレーションします。docker-compose.ymlでは`app`コンテナ起動時に`--install --idempotent`→`--upgrade`→通常起動という順でコマンドが連結されており、初回起動でDBが自動構築される仕組みです。公開側の購読ページやRSSアーカイブ(archive.go)はテンプレートレンダリングで配信され、認証はセッションベースでOIDCや2FA(auth.go)にも対応しています。
- STEP 01
`docker-compose.yml`をダウンロードして`docker compose up -d`を実行すると、Postgresコンテナとlistmonkアプリコンテナが順に立ち上がります。
- STEP 02
初回起動時にapp側コマンドが`--install --idempotent --yes`→`--upgrade --yes`→通常起動という順で自動実行され、DBスキーマが作られるのを待つことになります。
- STEP 03
ブラウザで`http://localhost:9000`を開くと、`LISTMONK_ADMIN_USER`と`LISTMONK_ADMIN_PASSWORD`を事前設定していなければ、初回セットアップ画面で管理者アカウントを作る必要があります。
- STEP 04
ログイン後はダッシュボードが表示され、リスト作成・購読者インポート(CSV)・SMTP設定・キャンペーン作成という流れで操作することになります。
- STEP 05
キャンペーンを送信すると、設定したSMTP経由でメールが配信され、バウンスWebhookを設定していればバウンス記録が`cmd/bounce.go`の処理を通じてDBに蓄積されます。
- STEP 06
公開購読ページやキャンペーンアーカイブRSSは`cmd/archive.go`のハンドラでレンダリングされ、設定次第で外部公開できます。
手元で動かすと、PostgreSQLをバックエンドに持つ単一バイナリのメール配信基盤が立ち上がり、管理UIからリスト・購読者・キャンペーン・テンプレート・ユーザー権限を一通り操作できる状態が得られます。SMTPさえ設定すればニュースレター配信やトランザクションメール送信、バウンス管理、公開購読フォーム、キャンペーンアーカイブRSSまで動く構成が手に入ります。
実際のメール送信にはSMTPサーバーの設定が別途必要で、docker-compose.ymlにはSMTP設定が含まれていないため、Settings画面での追加設定が前提になります。
`--install --idempotent --yes`は初回のみDBを構築する設計ですが、既存DBがある環境で誤った接続先を指定すると意図しないマイグレーションが走る可能性があるため、本番導入前に`db__host`などの接続情報を十分確認したほうがよいです。
バウンスWebhook(BounceWebhook)は`a.bounce`がnilだと503を返す設計なので、バウンス処理を使うには事前に該当機能を設定で有効化する必要があります。
READMEやファイルツリーからはfrontendにCypressのE2Eテスト一式(frontend/cypress/e2e)が揃っていることが確認でき、UI動作の裏付けとして参照できますが、今回のレビューでは実行結果までは確認していません。
自前のサーバーやVPSでメール配信基盤を持ちたい小〜中規模チームに向いています。Docker Composeだけで導入でき、管理画面・購読者セグメント・バウンス処理・多言語対応まで含まれる点は、READMEと実コードの整合性から裏付けが取れます。ソースコードのハンドラ構成(cmd配下)とdocker-compose.ymlの起動シーケンスが一致しており、「単一バイナリ+Postgres」という触れ込みは実体を伴っていると判断できます。ただしSMTP設定やバウンス機能の有効化など、起動後に自分で詰める作業は残るため、完全な「ゼロコンフィグ」を期待すると差を感じる可能性があります。