カテゴリー: Linux Page 1 of 53

【改訂・再編集】ApacheにWAF・Mod_Security導入。

こちらの記事の改訂・再編集版です。

そもそもWAFとは?

WAFとはWeb Application Firewallの略で、Webアプリケーション層の脆弱性を狙った攻撃を防ぐためのセキュリティシステムです。

  • UFWやFail2banがIPアドレスやポート番号といった家の玄関を監視するのに対し、WAFは、Webサーバーへ届く手紙(HTTPリクエスト)の中身を解析し、悪意あるスクリプトやコマンドの有無をチェックします。
  • UFWでは、通常のポート(80番や443番)を通る攻撃は防げませんが、WAFは攻撃の内容を解析し、独自のルールセットに基づき「このアクセスは許可するが、このコードがアクセスすることは許可しない」という、より柔軟で厳しいセキュリティチェックを施します。

この機能により、Webサーバーやアプリケーション本体に脆弱性が見つかったとしても、WAFが前段の盾としてこれをカバーできます。

ModSecurityとは?

ModSecurityは、IIS/Apache/Nginxといった主要なWebサーバープログラムにモジュールとして組み込みが可能なオープンソースのWAFです。

  • 導入コスト: ライセンス費用が不要であり、既存のWebサーバーと連携する形で容易に組み込めます。
  • 柔軟性: OSSであるため、高い柔軟性を持ち、設定(チューニング)次第でピンポイントの防御や包括的な防御を併せ持つことができます。

備考(バージョンの選択):

本稿で導入するModSecurityは、Ubuntu 24.04系のパッケージ管理で提供されるEOL (End-of-Life) となっているv2ですが、機能性は単一VPSの防御としては十分です。

v3への移行は、セキュリティ強度とメンテナンス性を考慮し、パッケージ化ないしはOSアップデートなどのタイミングでまた後日検討していきます。

環境

  • Ubuntu 24.04 (22.04でも動作確認)
  • Apache 2.4

※ パッケージ管理にaptitudeを用いています。必要に応じてaptに読み替えてください。

さっくりとした手順

  1. mod_securityのインストールを行います。
  2. mod_securityの設定を行います。
  3. Apacheのバーチャルサイトにmod_securityを組み込みます。
  4. 設定を反映して動作を確認します。

mod_securityのインストールを行います。

  • パッケージ全体のアップデート
sudo aptitude update
  • mod_securityインストール
sudo aptitude install libapache2-mod-security2
  • インストール確認
sudo apache2ctl -M |grep security
security2_module (shared)

と表示されていることを確認します。

ModSecurityの設定

  • 設定ファイル書き換え
sudo mv /etc/modsecurity/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf

推奨ファイルをそのまま設定ファイルとして書き換えます。

OWASP Core Rule Set (CRS)のインストールと設定

  • ディレクトリ移動
cd /usr/share/modsecurity-crs && pwd
  • ルールセットのダウンロード
sudo git clone https://github.com/coreruleset/coreruleset.git
  • ルールセットの設定書き換え
sudo mv /usr/share/modsecurity-crs/coreruleset/crs-setup.conf.example /usr/share/modsecurity-crs/coreruleset/crs-setup.conf

mod_securityモジュールにCRSを読み込む設定を追記

  • ディレクトリ移動
cd /etc/apache2/mods-available/ && pwd
  • ファイルのバックアップ
sudo cp -pi security2.conf /path/to/backup/directory/security2.conf.$(date +%Y%m%d)

任意のバックアップディレクトリを指定します。

  • バックアップ確認
diff -u /path/to/backup/directory/security2.conf.$(date +%Y%m%d) security2.conf

エラーがなければバックアップは成功です。

  • ファイル追記

/etc/apache2/mods-available/security2.confを、以下の差分になるように教義・信仰に沿ったエディタで編集します。(要root権限)

 <IfModule security2_module>
-       # Default Debian dir for modsecurity's persistent data
-       SecDataDir /var/cache/modsecurity
+    # Default Debian dir for modsecurity's persistent data
+    SecDataDir /var/cache/modsecurity

-       # Include all the *.conf files in /etc/modsecurity.
-       # Keeping your local configuration in that directory
-       # will allow for an easy upgrade of THIS file and
-       # make your life easier
-        IncludeOptional /etc/modsecurity/*.conf
+    # Include all the *.conf files in /etc/modsecurity.
+    # Keeping your local configuration in that directory
+    # will allow for an easy upgrade of THIS file and
+    # make your life easier
+    IncludeOptional /etc/modsecurity/*.conf

-       # Include OWASP ModSecurity CRS rules if installed
-       IncludeOptional /usr/share/modsecurity-crs/*.load
+    # --- OWASP Core Rule Set (CRS) の読み込み ---
+
+    # 1. CRSのセットアップファイルを読み込む(必須)
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/crs-setup.conf
+    
+    # 2. CRSのルールファイルを読み込む
+    #    パフォーマンス問題を起こすSQLデータ漏洩検知ルールを除外
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/REQUEST-*.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-950-DATA-LEAKAGES.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-952-DATA-LEAKAGES-JAVA.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-953-DATA-LEAKAGES-PHP.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-954-DATA-LEAKAGES-IIS.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-959-BLOCKING-EVALUATION.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-980-CORRELATION.conf
+    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-999-EXCLUSION-RULES-AFTER-CRS.conf

→ 修正後のsecurity2.conf全文

<IfModule security2_module>
    # Default Debian dir for modsecurity's persistent data
    SecDataDir /var/cache/modsecurity

    # Include all the *.conf files in /etc/modsecurity.
    # Keeping your local configuration in that directory
    # will allow for an easy upgrade of THIS file and
    # make your life easier
    IncludeOptional /etc/modsecurity/*.conf

    # --- OWASP Core Rule Set (CRS) の読み込み ---

    # 1. CRSのセットアップファイルを読み込む(必須)
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/crs-setup.conf

    # 2. CRSのルールファイルを読み込む
    #    パフォーマンス問題を起こすSQLデータ漏洩検知ルールを除外
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/REQUEST-*.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-950-DATA-LEAKAGES.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-952-DATA-LEAKAGES-JAVA.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-953-DATA-LEAKAGES-PHP.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-954-DATA-LEAKAGES-IIS.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-959-BLOCKING-EVALUATION.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-980-CORRELATION.conf
    IncludeOptional /usr/share/modsecurity-crs/coreruleset/rules/RESPONSE-999-EXCLUSION-RULES-AFTER-CRS.conf
</IfModule>

※ なぜここまで除外するか?

この、RESPONSE-9x系のルールは、ページの内容に機密情報(クレジットカードのデータなど)が入っていないかを精査します。

これは重要なものですが、昨今のAIボットによる過剰なクロールが挟むと、サーバそのものへの負荷を強め、更にログの圧迫(実際にサーバ容量120GB全てを食い尽くしました)とサーバダウンにつながります。

こちらは個人サイト、単一VPSの運用を旨としているため、ここに関するデータはオミットです。 その分、他の設定の補強でセキュリティ強度を担保します。

  • 設定追記の整合性を確認
sudo apache2ctl configtest

Syntax OKを確認します。

  • Apache再起動
sudo systemctl restart apache2.service
  • Apache再起動確認
systemctl status apache2.service

active (running) を確認します。

Apacheのバーチャルサイト編集

稼働済みのApacheバーチャルサイトの設定ファイルをいじります。バックアップ確認は入念に行ってください。

  • ディレクトリ移動
cd /etc/apache2/sites-available && pwd
  • バーチャルサイトの設定ファイルバックアップ
sudo cp -pi your_site.conf /path/to/backup/directory/your_site.conf.$(date +%Y%m%d)

.confファイルやバックアップディレクトリは自分の環境を指定します。

  • バックアップ確認
diff -u /path/to/backup/directory/your_site.conf.$(date +%Y%m%d) your_site.conf

エラーがなければバックアップは成功です。

  • ファイル追記

/etc/apache2/sites-available/your_site.confを、以下の差分になるように教義・信仰に沿ったエディタで編集します。(要root権限)

# Mod Security

## ModSecurity有効化
SecRuleEngine On
## ModSecurity検知モード
### 検知モードで動かす場合はSecRuleEngine Onをコメントアウトしてこちらを有効化します
#SecRuleEngine DetectionOnly

## ファイルのアップロードをできるようにします。
SecRequestBodyInMemoryLimit 524288000
SecRequestBodyLimit 524288000

## テスト用の検知パラメータを付け加えます。
    SecRule ARGS:modsecparam "@contains test" "id:4321,deny,status:403,msg:'ModSecurity test rule has triggered'"
  • ファイル差分
diff -u /path/to/backup/directory/your_site.conf.$(date +%Y%m%d) your_site.conf
+# Mod Security
+
+## ModSecurity有効化
+SecRuleEngine On
+## ModSecurity検知モード
+### 検知モードで動かす場合はSecRuleEngine Onをコメントアウトしてこちらを有効化します
+#SecRuleEngine DetectionOnly
+ 
+## ファイルのアップロードをできるようにします。
+SecRequestBodyInMemoryLimit 524288000
+SecRequestBodyLimit 524288000
+
+## テスト用の検知パラメータを付け加えます。
+    SecRule ARGS:modsecparam "@contains test" "id:4321,deny,status:403,msg:'ModSecurity test rule has triggered'"
+
  • 設定追記の整合性を確認
sudo apache2ctl configtest

Syntax OKを確認します。

  • Apache再起動
sudo systemctl restart apache2.service
  • Apache再起動確認
systemctl status apache2.service

active (running) を確認します。

mod_security動作確認

  1. ブラウザで、上記の設定を行ったWebサイトにアクセスし、閲覧できることを確認します。
  2. アドレスバーの末尾に?modsecparam=testを追加してアクセスします。

のように、アクセスできないことを確認します。

また、サーバでも

sudo cat /path/to/sites_log/directory/sites_error.log

※ログの格納場所やログの名前は自分の環境に合わせます。

を開き、

ModSecurity: Access denied with code 403 (phase 2). String match "test" at ARGS:modsecparam. [file "/etc/apache2/sites-enabled/your_site.conf"] [line "53"] [id "4321"] [msg "ModSecurity test rule has triggered"] [hostname "host_address"] [uri "/"] [unique_id "xxxxxxx"]

のように、エラーが発生していることを確認します。

備考

WordPress、Redmine等のWebアプリは自身の操作によって「不審なアクセス」として遮断することが極めてよくあります。(偽陽性)

そのため、テストを行った後は

## ModSecurity有効化
#SecRuleEngine On
## ModSecurity検知モード
### 検知モードで動かす場合はSecRuleEngine Onをコメントアウトしてこちらを有効化します
SecRuleEngine DetectionOnly

として検知モードとして動かした方が良いでしょう。

「インターネット接続をする際のApache設定」の常時SSL化とログ設定の手順(長文)

なぜ2020年代から(或いはその5年前から)常時SSL化が必須と言えるのか?

セキュリティの確保

  • 通信の暗号化
    • SSL/TLSの技術により、Webブラウザ~サーバ間の通信が暗号化。第三者による盗聴や改ざんを防ぎます。
  • 入力情報の保護
    • ログイン情報、個人情報、問い合わせフォームの内容など、機密性の高い情報のやりとりが安全になります。

ユーザーの信頼性向上

  • ブラウザの警告表示への対処
    • 2020年代より、Chrome/Safari/Edgeと言った主要なブラウザは従来のhttp通信を「保護されていない通信」としてブラウザに表示するようにしました。これは読者、アクセス者に対してユーザの不安を招きます。
  • 攻撃者にとっての絶好の餌を与えない
    • HTTP通信の状態であるというのは、攻撃者にとっての「オイシい」獲物です。ログイン情報やセキュリティの脆弱性などをより好んで狙うという状況を防ぎます。

(筆者には余り関係ないが) SEOへの影響

  • Googleを筆頭とする各種検索エンジンは、2014年以降、SSL対応を検索上位の評価要因に含めています。
  • HTTPS化されたサイトはSEOで有利になります。

Web標準としての定着

  • HTTPS by default機能
    • Chrome/Edge/ChromiumなどはHTTPSを標準接続とする仕様を導入。これにより、HTTPサイトはますます排除される傾向になります。

企業・サービスの信頼性維持

  • SSL化はもはや企業サイトの基本マナーとされています。
    • 未対応のままでは信頼性を損なう可能性があります。

余談 (私怨かつ直接的な動機)未対応企業への溜飲

  • 強烈なパワハラを喰らい去ることになった会社が「辞めてから10年経ってもHTTP通信のまま」というIT企業の存在は、「あんたは未だにHTTPS化をしていないわけ?」という精神的な勝利に繋がっています。
    • 器が小さいとかみみっちいと言われていても、かなり重要な動機です。

ログが重要な理由

トラブルシューティングが容易になる

  • 最も重視する項目です。先般の「記憶に頼るな。ログを信じろ」の全ての根拠です。
    • 特定のサイトでエラーが発生した場合、該当サイトのエラーログだけを確認できるため、原因特定が迅速になります。
  • バーチャルサイトごとにログがないと以下を招きます。
    • ノイズが多いことによる調査効率の低下。
    • 不審なアクセスの迅速な検知の非効率化。

セキュリティサービスとの連携

  • WAF連携
    • 筆者が用いているModSecurityの連携は、ひとえに「この、エラーログ・アクセスログ」を根拠にセキュリティの強化や利便性強化を図っています。
  • 攻撃のトレンドを知る
    • どのような攻撃があるからサーバはパフォーマンスが落ちているのか? を知る上でもこれは重要です。

サイトごとのアクセス解析が可能/容易になる

  • 複数のドメインやサービスを1台のサーバで運用している場合、ログを分けることで書くサイトのアクセス状況を個別に把握できます。
    • 例えば「example.com」と「sample.jp」のPV数や人気ページを比較したいとき、ログが分かれていないというのは分析が困難になります。

セキュリティ監査に対応しやすい

  • サイトごとにログを分けることで、不正アクセスや改竄の痕跡を個別に追跡可能です。
    • 仮に、何らかの法的なインシデントに巻き込まれたとしても、そのログを元に、迅速な対応が可能になります。

読者への回答

「これだけ長いのに何故2つに分けないのか?」は

  • SSL化
  • ログの設定

は、先に示した「加害者にならないための具体的手順」の1つ。「この両者は不可分であり、インターネットで公開する上では必須」だからです。

  • SSL化という2020年代セキュリティの標準
  • ログの可視化というインターネット黎明期から続くトラブルシューティングと解析

は絶対に必要な項目です。次ページから具体的な手順です。

Webサーバーの基盤設定:ディレクトリ変更とVirtualHostの目的(ローカル環境編)

Apacheの初期設定とWebコンテンツのルートディレクトリを変更する理由と、たとえサイトが一つでもVirtualHostを設定する必要性についてのメモです。

大前提「これはローカル環境での手順」です。

なぜなら、これはインターネット上サーバでの絶対的なルールが抜けています。

  1. https通信の対応
  2. ログ設定の未考慮

この2つは別の項でも解説しますが、これらを考慮しないと

  • 「管理が甘いサーバ」として攻撃者の格好の的になる
  • 「トラブル発生時の証跡をつかめない」

の2点が重くのしかかります。

理由1.なぜホームディレクトリ(DocumentRoot)を変更するのか?

標準でapacheを入れると、Webサーバーのコンテンツディレクトリとして使われるのは /var/www です。

しかし、本稿では/home/www-data へとホームディレクトリを変更します。これには、以下の明白な理由があります。

理由詳細
セキュリティ上の分離 (Preference)/var ディレクトリは、ログ(/var/log)や一時ファイル(/var/tmp)など、システムが頻繁に書き換える揮発性のデータを格納するために設計されています。Webコンテンツを /home に置くことで、システムデータとユーザーデータ(コンテンツ)を明確に分離し、万が一のシステム障害や冗長化の際に管理が容易になります。
ユーザープロファイルの整合性 (Practicality)www-data ユーザーは通常シェルログインできませんが、Ruby on RailsやNode.jsなどのモダンなアプリケーションbundle install やパッケージのインストールを行う際や、gitを利用する際に環境変数として自身のホームディレクトリを参照することがあります。これを /home/www-data に設定することで、アプリケーションがスムーズに動作し、予期せぬエラーを防ぐことができます。

理由2. なぜ単一サイトでもVirtualHost(バーチャルサイト)を仕込むのか?

VPS/ローカルサーバでで公開するサイトが一つだけであっても、デフォルトの設定ファイル (000-default.conf など) ではなく、個別のVirtualHost設定ファイルを作成して運用すべきです。

理由詳細
セキュリティ(デフォルト設定の無効化)デフォルト設定 (000-default.conf) は通常、/var/www/html を DocumentRoot としています。これを無効化し、カスタムVirtualHostのみを有効にすることで、意図しないディレクトリが公開されるリスクや、デフォルト設定のバージョン情報などが露出するリスクを防ぎます。
スケーラビリティと将来性将来、サブドメイン(例: blog.example.com)や別のドメインを追加する際に、既存の設定をコピーして修正するだけで済みます。最初からVirtualHostの構造を採用することで、設定の拡張が容易になり、メンテナンス性が向上します。
HTTPS(SSL)対応の必須要件HTTP(ポート80)からHTTPS(ポート443)への強制リダイレクトや、独自のSSL証明書の設定は、VirtualHostブロック (<VirtualHost *:443>) ごとに行うのが一般的です。VirtualHostが基本となることで、この必須のセキュリティ対策をスムーズに組み込めます。

さっくりとした手順

  1. ホームディレクトリの作成と設定
  2. /etc/passwdの書き換え(要注意)
  3. VirutalHostの設定
  4. 設定の有効化と確認

1. 新たなホームディレクトリの作成と設定

VPSのコンテンツ保存場所を /home/www-data に統一します。

  • ディレクトリ作成
sudo mkdir -p /home/www-data
  • ディレクトリの所有者変更
sudo chown -R www-data:www-data /home/www-data
  • 設定確認
ls -ld /home/www-data

 → 所有者がwww-dataになっていることを確認

2. /etc/passwd ファイルの書き換え

www-data ユーザーのホームディレクトリの定義を /var/www から変更します。

** 注意:** /etc/passwd はシステムアカウントを制御する重要ファイルです。必ずバックアップを取り、変更は一行のみであることを確認してください。

  • バックアップ作成
sudo cp -pi /etc/passwd /path/to/backup/directory/passwd.$(date +%Y%m%d)

→ 任意のバックアップディレクトリを指定します。また、$(date +%Y%m%d)を仕込むことで、「いつ」このバックアップを取ったかが明白になります。

  • バックアップ作成確認
sudo diff -u /path/to/backup/directory/passwd.$(date +%Y%m%d) /etc/passwd

→ 面倒でもこの作業は必須です。というのも、差分を取ることで「オリジナルとバックアップの両方が作成されている」というのを、コマンドという第三者の絶対的な目で見ることができるからです。

→ また、先ほどのcpと逆になっていることにも注意してください。これは、変更後に「どの行が惹かれ、どの行が足されたか」を明確化するためです。

  • sedによるファイル書き換え
sudo sed -i 's|/var/www|/home/www-data|' /etc/passwd

→ 特に注意が必要です。これをミスるとサーバ全体のロックアウトなども容易に発生します。

  • 書き換え確認
diff -u /path/to/backup/directory/passwd.$(date +%Y%m%d) /etc/passwd

差分が以下のみであることを確認します。

-www-data:x:33:33:www-data:/var/www:/usr/sbin/nologin
+www-data:x:33:33:www-data:/home/www-data:/usr/sbin/nologin

→ ここで、「なぜ、逆にして差分を取るのか」を明確化。

diff -u /etc/passwd /path/to/backup/directory/passwd.$(date +%Y%m%d)

とした場合、得られる情報は「まるで逆」になります。

+www-data:x:33:33:www-data:/var/www:/usr/sbin/nologin
-www-data:x:33:33:www-data:/home/www-data:/usr/sbin/nologin

となり、「バックアップの方が正しい修正」となってしまうからです。

3. VirtualHost 設定の準備(Redmineを例にする)

Redmine(動的アプリケーションの例)を /home/www-data 内のディレクトリで公開するためのベース設定を作成します。

cat <<- __EOF__ | sudo tee -a /etc/apache2/sites-available/redmine.conf
<VirtualHost *:80>
    ServerName 【hoge.example.com】
    # ServerNameは自身が設定したドメイン名に置き換えてください。

    DocumentRoot /home/www-data/redmine/public

    <Directory /home/www-data/redmine/public>
        # .htaccessによる設定変更を許可
        AllowOverride All
        # 複数Viewを無効化(アプリケーションのルーティングを優先させるため)
        Options -MultiViews
        # 全てのアクセスを許可
        Require all granted
    </Directory>
</VirtualHost>
__EOF__

4. 設定の有効化と確認

作成したVirtualHostを有効化し、デフォルトサイトを無効化します。

  • 既存のデフォルトサイトを無効化
sudo a2dissite 000-default.conf
  • 新しいサイト設定を有効化
sudo a2ensite redmine.conf
  • 構文チェック
sudo apache2ctl configtest

→ Syntax OKとなることを必ず確認してください。でないと、apacheサービスが停止したままとなってしまい、サービス断が発生します。

  • Apache サービス再起動
sudo systemctl restart apache2.service
  • Apacheサービス再起動確認
systemctl status apache2.service

active(running)を確認します。

これで、Apacheの基盤がセキュリティと運用効率を考慮したカスタム設定で動作するようになりました。

改訂・再編集『Ubuntu24.04にApacheをインストールするための具体的手順』

この記事を今のトレンドに合わせた上でのステップバイステップとした記事です。

概要

Ubuntu24.04にWebサーバーApacheをインストールします。最近のトレンドではNginxではあるものの、

  1. 豊富なモジュールとカスタマイズ
  2. 動的コンテンツの設定をしやすい
  3. 小規模サイトを立ち上げる上での手間の少なさ
  4. 外部ファイルやモジュールの連携により、以下のような細かい設定が可能
  • 自宅等からのアクセスログを残さず、ログの透明化を図る
  • Robots.txtを無視する悪質なクローラーの排除
  • mod_securityに代表されるWAF(Web Application Firewall)の設置

を考慮してのApache設定です。

さっくりとした手順

  1. (未実施の場合必須)UFWの設定を行います。
  2. Apacheのインストールを行います。
  3. Apacheの設定を行います。
  4. 設定の反映を確認します。

(未実施の場合必須)UFWの設定

この作業、サーバ移設などになれている人ほど陥る罠です。「設定はしっかりしている。なのにサンプルページすら引っかからない!」という場合、大概が「UFWでポート80/443を空けていない」パターンが大半を占めます。

大前提

SSH接続を許可(ポート22はSSH記事で許可済みを前提とする)。

設定の前の心構え:

UFWは堅牢であると同時に融通の利かない門番です。設定を間違えると「自分のサーバにログインできない」事態が易々と発生します。

そのため、この作業に臨む際は落ち着いて臨みましょう。コマンドを打つ際に3回ぐらい深呼吸してもいいぐらいの心構えです。

  • http通信を許可する
sudo ufw allow http comment 'Allow HTTP traffic for Apache'
  • https通信を許可する
sudo ufw allow https comment 'Allow HTTPS traffic for Apache'
  • 設定を確認する
 sudo ufw status verbose

上記、http/httpsが有効になっていることを確認します。

  • UFWが有効になっていない場合:有効化
sudo ufw enable 

インストールを行います。

  • パッケージ全体のアップデート
sudo aptitude update 
  • apacheのインストール
sudo aptitude install apache2
  • バージョン確認
apache2ctl -v
  • 表示例
Server version: Apache/2.4.62 (Ubuntu)
Server built:   2024-07-22T12:37:10
  • サービス稼働確認
systemctl status apache2.service

enabledactive (running)を確認します。

設定を行います。

  • 設定ファイルのバックアップ
sudo cp -pi /etc/apache2/apache2.conf /path/to/backup/directory/apache2.conf.$(date +%Y%m%d)

任意のバックアップディレクトリを指定します。

  • 設定ファイルのバックアップ確認
diff -u /path/to/backup/directory/apache2.conf.$(date +%Y%m%d) /etc/apache2/apache2.conf

差分が無いことでバックアップを確認します。

  • 設定ファイル追記
sudo tee /etc/apache2/apache2.conf > /dev/null << 'EOF'
ServerSignature Off
ServerTokens Prod
ServerName example.com  # <-- ここに実際のドメイン名またはホスト名を指定
EOF

自分のサーバー名を英数字で置き換えてください。

  1. サーバーの署名をオフにして
  2. 最小限の情報のみを公開し
  3. Webサーバの名前を指定する

内容です。

  • 追記確認
diff -u /path/to/backup/directory/apache2.conf.$(date +%Y%m%d) /etc/apache2/apache2.conf
  • 差分内容
+ ServerSignature Off
+ ServerTokens Prod
+ ServerName 自分のサーバー名

設定反映を確認します。

  • 構文確認
sudo apache2ctl configtest

Syntax OKを確認します。

  • サービス再起動
sudo systemctl restart apache2.service
  • サービス再起動確認
systemctl status apache2.service

active (running)を確認します。

  • 設定反映確認
curl -I http://localhost

以下のように、ServerヘッダーにApacheのみが表示されていることを確認します。

Server: Apache

単一VPSでインターネット公開のVPSの運用上の注意 または 「加害者にならないための心構え/具体的手順」。

はじめに

前回の続き。Linuxサーバ運用上の注意を述べましたが、更に難易度が上がり

「このLinuxサーバをインターネットで公開するとき」

の心構えについて述べます。

絶対的な違い:「インターネット上サーバの理不尽な非対称性」

そもそも、ローカル環境とインターネットにこれを公開するというのは

  • 技術
  • 倫理観
  • 運用の手間

が何もかも違います。その中で一番気をつけなければならないのは

「自分自身が加害者になってしまうこと」

です。これはもっと具体的に言うと

「管理者権限を乗っ取られ、自分のサーバが攻撃ツールのフロントエンド/バックエンドとして機能すること」

を意味します。攻撃者は自分自身が表立って行動することを嫌います。そのため、

  • 管理の甘いサーバ
  • 脆弱性があるサービス

などにつけ込み侵入を試み、それを自らの配下として利用します。これは、先に述べた

  • システムダウン
  • バックアップ不備による切り戻し不可

とは何もかもレベルが違うリスクです。

ぶっちゃけ、自分自身が運営しているサーバの瓦解は自分が泣けばそれで済む話ではありますが、自分が管理しているサーバが攻撃に関与したというのは、法的/金銭的/社会的な失墜が絡む大問題。

この、理不尽なまでの非対称性が絡むということを最初に意識してインターネット上サーバでの運営を意識しましょう。

趣味/勉強の範疇での最低限の手段

とはいえ、趣味や勉強の範囲でインターネット接続環境でもLinuxサーバを立ち上げたいという方はいるかと思います。

ここからは、メソロドジーから一歩踏み込み、「より具体的な手段」について述べます。

想定する環境

  • とりあえずLinuxサーバをvpsで立ち上げた。
  • 様々な環境から接続をするから確固たる固定IPを持っていない
  • それでもWebサーバを立ち上げたい

ちょっとした茨の道を進みたい方向けです。

※ ここからは筆者の過去記事から「特に必要な設定」を抜き出し、加筆編集を加えた記事です。※

話の前に筆者環境

  • Ubuntu 24.04
  • apt/aptitudeのパッケージ管理システム

を用います。つまり、makeやリビルドなどは発生しない、再現性の高い環境でのステップバイステップです。

メンテナンス用のユーザを作成する

この作業は極めて重要です。というのも、先に示したとおり、攻撃者が真っ先に/そして最終的に狙うのは管理者権限。つまり、(root)です。

rootへのネットワークを介したログインを禁止すると同時に、メンテナンス用のユーザを作成し、NW上からは、ここから接続することを厳命します。

  • (コンソールを利用して)ユーザ作成
adduser [メンテナンス用ユーザ]

[メンテナンス用ユーザ]は英数字です。その後、パスワード設定などを対話式で求められるので、指示に従って入力します。

  • ログイン確認
exit

物理コンソール/VPSのWebシリアルコンソールから抜けます。

メンテナンス用のユーザ作成確認(メンテナンス用のユーザ)

  • 作成したユーザでログイン確認

Webコンソールで、作成したユーザ名とパスワードでログインできることを確認。

whoami

で、設定したアカウントであることを確認します。

  • rootに昇格できないことを確認
sudo su -

としても、rootに昇格することはできません。なので、一度

exit

でコンソールを抜け、rootでログインし直します。

メンテナンス用のユーザのroot昇格設定(root)

  • メンテナンス用のユーザにsudoを追加

rootでログイン後、

usermod -aG sudo [メンテナンス用ユーザ]

で、sudoグループにこのユーザを加えます。

  • sudo追加確認
id -a [メンテナンス用ユーザ]

で、以下のように表示されることを確認します。

uid=1000(hoge) gid=1000(hoge) groups=1000(hoge),27(sudo),100(users)

修正したユーザのグループに、27(sudo)と表示されることがポイントです。

確認後、

exit

で更にrootを抜け、今度はメンテナンス用のユーザでログインします。

rootのロック (メンテナンス用のユーザ)

  • root昇格

メンテナンス用のユーザでログイン後、

sudo su -

で、rootに昇格できることを確認します。

whoami

root表示されることも確認します。

  • rootロック
passwd -l root

として、rootそのものをロックします。

  • rootのロック確認
exit

を2回行い、Webコンソールから抜けます。

rootロック確認

  • メンテナンス用のユーザ→Webコンソールでログイン可能
  • root→Webコンソールでログイン不可能を確認します。

これ以降はメンテナンス用のユーザで作業を行います。

SSH設定

Ubuntu Desktop系と違い、Ubuntu Serverではsshdがデフォルトでインストールされていない場合があります。

sudo apt install ssh

で、sshdをインストールします。

インストール後、

ssh -V

でバージョンが表示されることを確認し、

systemctl status ssh.service

で、runningenabledを確認します。

このSSHは鍵認証でログインできるようにします。この鍵認証のセキュリティ強度はパスワードと段違い。

鍵交換認証にする理由
  • パスワードが送信されない
    • パスワード認証では、パスワード自体がネットワーク上を流れるため盗聴リスクがあります。
    • 鍵認証では、秘密鍵が署名を生成し、署名のみが送信されるため、秘密情報が直接送られることはありません
  • 総当たり攻撃に強い
    • パスワードは文字数が少ないと短時間で破られる可能性があります。
    • 鍵認証では、2048ビット以上の鍵が使われることが多く、現在の一般的なサーバの計算能力では事実上破ることが不可能です。
  • 盗聴されても再利用できない
    • 鍵認証では毎回異なるチャレンジに対して署名を行うため、録音や再送信による攻撃(リプレイ攻撃)が通用しません。
  • フィッシング耐性が高い
    • パスワード認証は偽サイトに入力してしまうリスクがあります。
    • 鍵認証では秘密鍵がローカルに保管されており、外部に送信されないためフィッシングに強いです。

SSH鍵ペア作成

ssh-keygen -t ed25519
  • 鍵の格納場所は空Enter。(/home/hoge/.ssh/
  • パスワードを設定します。

SSH鍵ペア作成確認

  • 鍵格納ディレクトリに移動
cd .ssh
  • ファイルの内容確認
ls -l

以下のファイルを確認します。

  1. id_ed25519
  2. id_ed25519.pub ※これらのファイルはscp等で自分のクライアントにコピーします。

鍵の設定変更

公開鍵をauthorized_keysに変更し、パーミッションを厳密にします。

  • ファイル名変更
cat id_ed25519.pub >> authorized_keys
  • パーミッション設定
chmod 600 authorized_keys

秘密鍵の保存

この秘密鍵(id_ed25519)は、サーバー全体のアクセス権を持つ、言葉通りの意味でのマスターキーです。

この秘密鍵を奪われることは、サーバーの全権限を奪われることと同義です。 そのため、管理は厳密に、そして自分だけがアクセスできる安全な手段(パスワードマネージャーや暗号化されたストレージなど)で、必ずバックアップをこの段階で行ってください。

その後、適切なターミナルクライアントでこの秘密鍵を登録。接続を確認できたという確証が取れて、初めて実機の前から解放されます。

UFWとFail2banの設定

  1. ファイアウォール(ufw)の設定: 不要な通信をすべて拒否し、必要な通信(SSH, HTTP/S)のみを許可する、基本的な防御壁を構築します。
  2. 不正アクセスの自動検知・ブロック(fail2ban): ログファイルを常時監視し、不審なアクセス元を検知すると、ufwと連携してそのIPアドレスからのアクセスを動的に、そして恒久的にブロックします。
    • SSHへのログイン失敗(3回)
    • ufwがブロックした通信(1回)

Fail2banとは?

fail2banは、サーバーのログファイルを監視し、設定されたパターンに一致する不審なアクセス(パスワード総当たり攻撃など)を検知すると、そのアクセス元のIPアドレスを自動的にファイアウォールの拒否リストに追加する、侵入防止ソフトウェアです。
一度設定すれば、アンインストールしない限りは有効化し続けます。

まず、サーバーの玄関となるファイアウォールufwを設定します。

0-1. システム全体のバックアップ(vpsや仮想サーバの場合)

UFWとfail2banは基本的である分、設定に極めて忠実です。そのため、設定をミスして自分自身のアクセスを禁止した場合、そこに入るための手段はなくなります。

そのため、vps/仮想サーバと言った物理的なログイン手段を持たない場合は、スナップショットやディスクイメージ全体のバックアップを行い、「失敗したときのリカバリー」を行えるようにします。

現に、筆者は、これを怠ったばかりにサーバを作り直したことが3回ほどあります。

0-2. 実機でログインできる準備をしておく(物理サーバの場合)

物理サーバで、サーバ室やデータセンターなどの場合は、この設定が終わるまでは実機の前にいるべきです。

1.1 デフォルトのポリシーを設定

最初に「入ってくる通信は原則すべて拒否、出ていく通信はすべて許可」という基本方針を設定します。これが最も安全な基本設定です。

  • 入ってくる通信を全拒否
sudo ufw default deny incoming
  • 出てくる通信を全許可
sudo ufw default allow outgoing
  • ufw.logの有効化
sudo ufw logging on

これを行わないと、後述するfail2banのアクセスがうまくいきません。

1.2 必要な通信を許可する

次に、必要なサービスへの通信を個別に許可します。SSHの接続を許可する前にufwを有効化すると、サーバーから締め出されてしまうので、必ず先に設定してください。

  • SSH接続を許可(ポート22番)
sudo ufw allow ssh comment 'Allow SSH connections'
  • WebサーバーへのHTTP接続を許可(ポート80番)
sudo ufw allow http comment 'Allow HTTP traffic'
  • WebサーバーへのHTTPS接続を許可(ポート443番)
sudo ufw allow https comment 'Allow HTTPS traffic'

commentオプションで、後からルールを見返したときに分かりやすいようにコメントを付与できます。

これはもちろん基本的な構成です。他のポートを開放・閉じる場合は必要に応じて行います。

1.4 UFWを有効化

ルールを設定したら、ufwを有効化します。

sudo ufw enable

実行すると、「この操作は既存のSSH接続を切断する可能性があります」という警告が出ますが、ステップ1.2でSSHを許可していれば問題ありません。yを入力して実行します。

1.5 設定状態の確認

最後に、設定が正しく反映されているか確認します。

sudo ufw status verbose

Status: activeと表示され、許可したルールが一覧に出ていれば成功です。

1.6 ufw有効化確認

SSHターミナルで

telnet localhost 22

と行ってみます。

Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.

と通信が可能です。逆に、通信を許可されていないポートでは

telnet localhost 23
Trying 127.0.0.1...
telnet: Unable to connect to remote host: 接続を拒否されました

として、接続することはできません。

手順2:Fail2banのインストールと設定

次に、fail2banをインストールし、ufwと連携させる設定を行います。

2.1 Fail2banのインストール

  • パッケージリストを更新
sudo aptitude update
  • fail2banをインストール
sudo aptitude install fail2ban

筆者の好みでaptitudeを用いていますが、aptでも同様です。

2.2 設定ファイルの仕組み(.conf と .local)

Fail2banの設定は、/etc/fail2ban/ディレクトリにあります。重要なルールとして、jail.confのような.confファイルを直接編集してはいけません。

代わりに、jail.localのように.localという拡張子のファイルを作成し、変更したい項目だけを記述します。.localファイルの内容が.confの内容を上書きする仕組みになっており、これにより、将来Fail2banがアップデートされても、自分が行ったカスタム設定が消えてしまうのを防げます。

2.3 jail.localの作成と解説

教義・信仰に沿ったエディタで、/etc/fail2ban/jail.local というファイル名で新規作成し、以下の内容を記述します。

# SSHへの総当たり攻撃を監視・ブロックする設定
[sshd]
enabled   = true               # このsshd用の設定を有効にする
maxretry  = 3                  # 3回試行を失敗したら
bantime   = -1                 # 無期限にBANする
logpath   = /var/log/auth.log  # この認証ログファイルを監視する
ignoreip  = 127.0.0.1/8 ::1 【ここに自分のIPアドレスを追加】
# ignoreipには、絶対にBANしたくない自分のIPアドレスなどをスペース区切りで指定

# UFWがブロックしたログを監視・ブロックする設定
[ufw]
enabled   = true
filter    = ufw-aggressive
action    = iptables-allports
logpath   = /var/log/ufw.log
maxretry  = 1                  # 1回でもUFWの拒否ログに記録されたら
bantime   = -1                 # 無期限にBANする
ignoreip  = 127.0.0.1/8 ::1 【ここに自分のIPアドレスを追加】

2.4 カスタムフィルターの作成(ufw-aggressive)

上記の[ufw]セクションで指定したufw-aggressiveというフィルターは、自分で作成する必要があります。これは、ufw.logから攻撃元IPアドレスを抜き出すためのルールです。

/etc/fail2ban/filter.d/ufw-aggressive.conf というファイル名で新規作成し、以下の内容を記述します。

[Definition]
failregex = [UFW BLOCK].+SRC=<HOST>
ignoreregex =

failregex: この正規表現パターンに一致するログ行を探し、<HOST>の部分を攻撃元IPアドレスとして認識します。

手順3:設定の反映と動作確認

  1. Fail2banサービスを有効化・起動します。
  • fail2banの有効化(サーバ再起動でも自動的に起動するようにする)
sudo systemctl enable fail2ban
  • fail2banの起動
sudo systemctl start fail2ban
  1. サービスの稼働状態を確認します。
sudo systemctl status fail2ban

active (running)と表示されていれば成功です。

  1. ジェイル(監視)の状態を確認します。
sudo fail2ban-client status

Jail list:に、sshdufwが表示されていれば、監視が開始されています。

これで、不審なアクセスは次回以降、有無を言わせずブロックされる設定となりました。
BANされたIPアドレスは sudo fail2ban-client status sshdsudo fail2ban-client status ufw で確認できます。

まとめ「大いなる力には……」

Linuxの学習で実機を触った方(特にRocky/AlmaなどのRHEL系ディストリビューション)で

sudo su -

を実行したとき、以下のような文言を見かけるのではないでしょうか。

あなたはシステム管理者から通常の講習を受けたはずです。
これは通常、以下の3点に要約されます:
    #1) 他人のプライバシーを尊重すること。
    #2) タイプする前に考えること。
    #3) 大いなる力には大いなる責任が伴うこと。

この#3の「with great power there must also come -- great responsibility」は特に重要です。

少なくとも、Linuxサーバのインターネット公開という「1つの世界」を「他の世界と接続する」行為を試みた者は、この言葉を言葉ではなく魂で理解していきましょう。

余談(という名の本題)

なお、これを力説するのは「筆者が加害者になりかけたことがある」からです。上記の設定などを全く理解せず、rootの意味/覚悟を知らぬままLinuxサーバを自宅から運用するということを行ってしまったため……

たちまちのうちに制御を乗っ取られ、「善意の第三者からの通報」により阻止されたという苦い思いがあります。

この経験は15年もの間、Linuxと筆者を遠ざけ、趣味で触ってもローカル環境で運用するというトラウマとなりました。

ようやく、このトラウマから脱却できつつあるので、初心に立ち返る意味でもこの文章を残します。

BookStackサイトの404を差し替え。

BookStackの404記事を自分好みの文章に差し替えたときのメモです。

環境

  • BookStack v25.07.2
  • PHP8.3
    • PHP-FPM
  • Apache 2.4
    • 実行ユーザはwww-data
  • MySQL 8
  • Ubuntu 24.04

さっくりとした手順

  1. BookStackの404ページへと移動します。
  2. 元々の404ページを退避させます。
  3. カスタム404へと差し替えます。
  4. 設定を反映させます。
  5. 内容を確認します。

BookStackのディレクトリ移動と元ファイルの退避

  • ディレクトリ移動
cd /path/to/BookStack/resources/views/errors/ && pwd

自分の環境に合わせます。(筆者環境/home/www-data/BookStack/resources/views/errors/)

  • 404ページの退避
sudo mv 404.blade.php /path/to/backup/404.blade.php.$(date +%Y%m%d)

ファイル全体を差し替えるので、mvを利用します

  • 404ページの退避確認
ls -l /path/to/backup/404.blade.php.$(date +%Y%m%d)

ファイルがあることを確認します。(mvなのでlsで確認)

404ファイル作成

  • 404.blade.php

を、新たなファイルに差し替えます。筆者はこのようにしました。

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>404 | もう逃げられない、アーサー</title>
    <style>
        /* 全体設定 */
        body {
            font-family: 'Times New Roman', Times, serif;
            background-color: #f7f7f7;
            color: #333;
            margin: 0;
            padding: 20px;
            line-height: 1.6;
        }

        /* コンテナ */
        .container {
            max-width: 800px;
            margin: 40px auto;
            background-color: #fff;
            padding: 30px;
            box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1);
            border: 1px solid #ddd;
        }

        /* 404ヘッダー */
        .header {
            text-align: center;
            margin-bottom: 30px;
            border-bottom: 2px solid #a00; /* 赤いライン */
            padding-bottom: 10px;
        }

        .header h1 {
            font-size: 3em;
            color: #a00;
            margin: 0;
        }

        .header p {
            color: #666;
            font-style: italic;
        }

        /* 対話スタイル */
        .dialogue-box {
            margin-bottom: 20px;
            padding: 15px;
            border-left: 5px solid;
        }

        .dialogue-box.editor {
            border-color: #4CAF50; /* 緑色 (編集者/外部の声) */
            background-color: #e8f5e9;
        }

        .dialogue-box.arthur {
            border-color: #2196F3; /* 青色 (アーサー/コナン・ドイル) */
            background-color: #e3f2fd;
        }

        .speaker {
            font-weight: bold;
            display: block;
            margin-bottom: 5px;
            font-size: 0.9em;
            text-transform: uppercase;
        }

        /* 結びのフッター */
        .footer {
            text-align: center;
            margin-top: 30px;
            padding-top: 20px;
            border-top: 1px dashed #ccc;
        }

        .footer a {
            color: #007bff;
            text-decoration: none;
            margin: 0 10px;
            font-weight: bold;
        }

        .footer a:hover {
            text-decoration: underline;
        }

    </style>
</head>
<body>

    <div class="container">

        <div class="header">
            <h1>404 Not Found</h1>
            <p>ページが見つかりません。探偵の不在は、常に混乱をもたらします。</p>
        </div>

        <div class="dialogue-box editor">
            <span class="speaker">編集者(あるいは「声」)</span>
            <p>**もう逃げられない。**<br>
            続きを書け。馬車でストランドの編集部へ行こう。<br>
            よく考えろ。自宅は葬列で包囲されている。<br>
            喪章をつけたロンドン市民が続きを望んでいるんだ。<br>
            君は探偵の大敵を出した直後に滝に落として、雑誌に大損害を与えた。<br>
            もういい、歴史小説は終わりだ。<br>
            **ホームズを生還させるんだアーサー。**<br>
            君は既に有名作家として評価されているんだ!<br>
            母上からの手紙を読め。読むんだ!<br>
            母上も探偵の話を続けろと言っているぞ。<br>
            ファンから殺されたいのか?<br>
            君の作家性を高めるんだ!</p>
        </div>

        <div class="dialogue-box arthur">
            <span class="speaker">アーサー・コナン・ドイル</span>
            <p>**未だ何も評価されちゃいないんだ! 何も!**<br>
            俺にとって本当の小説とは戦争小説のことなんだ!<br>
            アレは俺の小説じゃ無かった!<br>
            生活費を稼ぐため、もっと書けと頼まれた!<br>
            俺は100年戦争小説の為にリアルな騎士道を学び尽くした!<br>
            これを書くために自キャラを滝に落としたら蛆虫どもが非難してくるんだ。<br>
            俺のことを探偵殺しとか駄文を書く暇あったら生き返らせろとか悪口の限りを並べやがった!<br>
            あいつら何なんだ?<br>
            歴史物のなんたるかも知らずに!<br>
            **頭にきたぜ!**</p>
        </div>

        <div class="dialogue-box editor">
            <span class="speaker">編集者(あるいは「声」)</span>
            <p>君にとってホームズの物語は<br>
            **今の栄光の時代だ。断じて過去にはない**</p>
        </div>

        <div class="dialogue-box arthur">
            <span class="speaker">アーサー・コナン・ドイル</span>
            <p>俺は**大英帝国の未来**を書きたいんだ!</p>
        </div>

        <div class="dialogue-box editor">
            <span class="speaker">編集者(あるいは「声」)</span>
            <p>未来? 未来だと?<br>
            君はまだ少年兵のように、戦場に夢を見ているのか?<br>
            ペンで帝国を救うつもりか、アーサー?</p>
        </div>

        <div class="dialogue-box arthur">
            <span class="speaker">アーサー・コナン・ドイル</span>
            <p>救うだと? 違う! **断罪する**んだ。<br>
            俺は帝国の瓦礫の上で、真実の騎士を描く!<br>
            硝煙の中に詩を見た。あの幻を、誰も読もうとしなかった。<br>
            ホームズは観察するだけだ。<br>
            だが俺の騎士は、**行動する!**</p>
        </div>

        <div class="footer">
            <a href="/">本棚へ戻る (Go Home)</a>
            <p style="font-size:0.8em; margin-top:10px;">(探偵は...未だ見つかっていません。)</p>
        </div>
    </div>

</body>
</html>
  • 404.blade.phpの所有者変更
sudo chown www-data:www-data 404.blade.php && ls -l 404.blade.php

www-dataはBookStackの実行ユーザに合わせます。合わせた後、所有者を確認します。

設定反映

  • artisanによるキャッシュクリア
sudo -u www-data php artisan view:clear
sudo -u www-data php artisan cache:clear

設定反映確認

BookStackのサイトにアクセスし、存在しない適当な文字を入れます。

上記、設定した文書があることを確認します。

Linuxサーバ設定変更時に心がけていること。

趣味と実益を兼ねたVPS運用。その核となる心構えについての個人的なメモを、具体例を交えつつ方法論(メソドロジー)について記しています。

  • Linuxの基本的な知識はあると思う
  • Linuxサーバを個人で運用したい
  • チューニング、設定変更、パッケージ管理のコツを知りたい
  • 管理者は自分一人を想定している

方の参考になれば幸いです。

壊れる前の切り戻しの準備。

これが基本かつ重要な心構えです。

  • プログラム1つの更新
  • 設定ファイルの修正
  • コマンドミス

などで、サーバは瓦解します。しかも、自分の指先一つで壊れるのですから、何があっても

誰かのせいにしたいが自分の顔しか思い浮かばない
I'm casting around in my head for someone to blame and it's just me, keeps coming back at me.

という状況です。筆者が手順メモで

sudo cp -pi /etc/something/imporotant/config.file /path/to/backup/config.file.$(date +%Y%m%d)

とバックアップを取り、

diff -u /path/to/backup/config.file.$(date +%Y%m%d) /etc/something/imporotant/config.file

と、diffで差分を取るのは「何を変更しても(戻せる範囲で)切り戻せる」を体でたたき込んでいるからです。

バージョンアップ時にmysqldumpでDBのバックアップを取ったり、ディレクトリごと/サーバのイメージごとバックアップを取るなどもその表れです。

「何を」実行するのではなく「どこで」実行するか?

ふわっとしていますが、以下の状況を考えましょう。

/tmpディレクトリで

sudo rm -rf *

を実行するのと、

/etc/apache2/sites-available ディレクトリで

sudo rm -rf *

を実行するのでは、その後のサーバの状況(というよりも惨劇)がまるで違います。

「このコマンドを実行するのか」以上に「どのディレクトリでこれを実行するのか」を念頭に置いて、

cd /var/log && pwd

(cd /var/log ; pwdでも可)

を実行する習慣は極めて大事です。或いは、

/etc/profile.d/pwd.sh等のシェルスクリプトを作り、

#!/bin/bash

# カスタムcd関数を定義
cd() {
    # ビルトインcdコマンドの実行
    builtin cd "$@" || return

を登録しておけば、

cd /var/log

と実行するだけで、

cd /var/log && pwd

と同じ効果が得られます。

それ以上に大切な「いつ実行したか?」

「いつ」実行したかは「何を」よりも「どこで」実行したかよりも大事な証拠となり得ます。

設定がおかしくなった、または復旧したかのトリガーは

「いつ、何かをやったか」に、historyコマンドに明確に現れています。

また、これが、上述したバックアップしたときに

sudo cp -pi /etc/something/imporotant/config.file /path/to/backup/config.file.$(date +%Y%m%d)

と、$(date +%Y%m%d)変数をつけてまでファイルの変更管理を行うのは、その表れです。

チューニング時、「どの数値まで耐えられたか?」を記録するための多いな助けになります。

手順化するときは1コマンド1行。

復旧手順、慣れている作業ほど陥りやすいミスです。

こちらはサーバの証明書の整合性を確認するためのコマンドメモですが

  • 期限が延びていることを確認
openssl x509 -noout -dates -subject -in example.com.crt.$(date +%Y%m)
  • 証明書から公開鍵を取得
openssl x509 -pubkey -in example.com.$(date +%Y%m) -noout | openssl md5
  • 秘密鍵から公開鍵を取得
openssl pkey -pubout -in example.com.$(date +%Y%m) | openssl md5

と、1行に書くことで、視認性や意図が明確になります。これが

# 期限が延びていることを確認

openssl x509 -noout -dates -subject -in example.com.crt.$(date +%Y%m)

# 証明書から公開鍵を取得

openssl x509 -pubkey -in example.com.$(date +%Y%m) -noout | openssl md5

# 秘密鍵から公開鍵を取得

openssl pkey -pubout -in example.com.$(date +%Y%m) | openssl md5

と書かれていたら、1行ずつコピーする羽目になり、作業時の手間と効率化がまるで違います。

特に:サーバのバックアップ、復旧、切り戻しといった緊急と正確さが要求される状況下では、手順作成時のちょっとした手間がストレスを大きく軽減します。

最後に「記憶に頼るな、ログを信じろ」

  • 何かおかしい
  • 突然サーバが止まった
  • 誰かが攻撃している?

などのほぼ全ての証跡はログに残されています。ログに残っていなければその途絶えたところが証拠です。(いわゆる『吠えなかった犬の推理』)

例えば、先日、Nextcloudのレスポンスが悪い、という時の決定的な証拠は/var/log配下のphp8.3-fpm.logに現れていました。

[04-Oct-2025 17:32:36] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[04-Oct-2025 18:45:55] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[04-Oct-2025 21:28:57] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it

これにより、PHP-FPMのプールの設定値に問題があったと特定できたのです。

何か怪しいと思ったら自分の設定値と同時に/var/log配下の関連しそうなところを確認しましょう。

そして、ログをそのままググり、どこかで誰かがエラーを元に解決策を残しているという期待もしましょう。

まとめ

と、わりとさっくりとした言い方ではありますが、

  • 切り戻せる姿勢
  • バックアップの大切さ
  • 手順の明確さ
  • タイムスタンプ

という4本の柱をメインにすれば、まず問題は無いかと思います。

『むこうぶち』の中にも

「船が陸にたどり着く寸前に生憎の嵐…… どうすればいいと思います?
いったん沖に引き返すんですよ
船ってのは水に浮かぶようにできているんです
無闇に上陸を焦って座礁する事が一番怖い」

は、サーバ運用にも通じるアナロジーとなっています。

ユースケース:PHP-FPMプール設定引き上げによるNextcloudのレスポンス改善

環境

  • Nextcloud 31系
  • PHP 8.3
    • PHP-FPM 8.3
  • Redis / APCUなどによる
  • Apache 2.4
  • Ubuntu 24.04
  • MySQL 8
  • メモリ6GB
  • 4 core CPU

事象

Nextcloud Talkを含めたレスポンスが非常に悪いという状況。具体的には

  • トップページがなかなかロードされない。
  • 各画面の遷移状態が悪い。
  • 画像をクリックしても表示に時間がかかる。(分単位であることも)

free -hでもメモリ圧迫という様子を見せず、topをたたいても異常なし。

何よりも、同一サーバに同居する

  • Growi
  • Redmine
  • BookStack

などが正常に動いていて、これらはレスポンスも良好。サーバの性能ではなく、サーバ以外のところに原因があると考え、調査開始です。

原因究明

答えは/var/log配下のphp8.3-fpm.logに現れていました。

[04-Oct-2025 17:32:36] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[04-Oct-2025 18:45:55] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it
[04-Oct-2025 21:28:57] WARNING: [pool www] server reached pm.max_children setting (5), consider raising it

これにより、PHPのリクエストを処理するワーカープロセスの数が上限(5)に達し、リクエストが滞留していることがパフォーマンス低下の直接的な原因だと特定しました。

これが分かれば、後は実際の対処です。

事象改善:さっくりとした手順

  1. PHP-FPMのプール設定ファイルのバックアップを取ります。
  2. 設定ファイルを編集してワーカープロセスの上限数や他の関連する値を引き上げます。
  3. 設定ファイルを反映させるため、各種サービスを再起動します。
  4. 事象の解決を確認します。

設定ファイルのバックアップ

  • ファイルバックアップ
sudo cp -pi /etc/php/8.3/fpm/pool.d/www.conf /path/to/backup/directory/www.conf.$(date +%Y%m%d)

※php-fpmの設定値は、入れているPHPのバージョンによって異なります。自分の環境に合わせたものに修正してください。

 → /home/hoge/backupなど、任意のバックアップディレクトリを指定します。

  • ファイルバックアップ確認
diff -u /path/to/backup/directory/www.conf.$(date +%Y%m%d) /etc/php/8.3/fpm/pool.d/www.conf

 → エラーがなければバックアップが取れています。

備考:なぜdiffを用いてバックアップの確認をするのか?

  • ls -lよりも確実に、元ファイルとバックアップファイルがあるか「両方のファイル」で確認を取るため。
  • 編集後、「どのような編集を行ったのか?」を同じコマンドで確認を取る。
    • 「バックアップ」-「設定ファイル」の順番とすることで、後のdiffの編集を行った、追記を行った箇所が+で表示されます。(同様に削った箇所が-で表示)

特に、設定ファイルの修正は非常にデリケートな問題であり、下手な設定がサーバ全体のシステムダウンを引き起こします。このため、変更管理や後のトラブルの追跡を兼ねてのバックアップはサーバメンテナンスの黄金律として体に覚え込ませましょう。

ファイルの修正

  • ファイルの修正

上記、バックアップを取った後の 元ファイル /etc/php/8.3/fpm/pool.d/www.conf を、管理者権限で、自身の教義・信仰に基づいたエディタで修正します。

こちらの設定値は、aptなどでのパッケージ管理システムでのインストールであれば、

pm.max_children = 5
pm.start_servers = 2
pm.min_spare_servers = 1
pm.max_spare_servers = 3

となっていることが多いです。これを、以下のように修正しましょう。

pm.max_children = 15
pm.start_servers = 4
pm.min_spare_servers = 2
pm.max_spare_servers = 6

※ サーバ環境などにより、随時、修正を行ってください。

修正後、保存を行います。

  • diffによる差分確認
diff -u /path/to/backup/directory/www.conf.$(date +%Y%m%d) /etc/php/8.3/fpm/pool.d/www.conf

以下のような差分を確認します。

; Note: This value is mandatory.
-pm.max_children = 5
+pm.max_children = 15

 ; The number of child processes created on startup.
 ; Note: Used only when pm is set to 'dynamic'
 ; Default Value: (min_spare_servers + max_spare_servers) / 2
-pm.start_servers = 2
+pm.start_servers = 4
 ; The desired minimum number of idle server processes.
 ; Note: Used only when pm is set to 'dynamic'
 ; Note: Mandatory when pm is set to 'dynamic'
-pm.min_spare_servers = 1
+pm.min_spare_servers = 2
 ; The desired maximum number of idle server processes.
 ; Note: Used only when pm is set to 'dynamic'
 ; Note: Mandatory when pm is set to 'dynamic'
-pm.max_spare_servers = 3
+pm.max_spare_servers = 6 
 ; The number of rate to spawn child processes at once.
 ; Note: Used only when pm is set to 'dynamic' 

このように、修正前が-の行、修正後が+の行で修正されていることが分かります。この数値や設定以上に重要なのは「変なスペースや意図した設定以外の情報が含まれていないか?」を、自分の修正した記憶を頼りにすることではなく、コマンドという絶対的な第三者の目で確認することです。

設定反映

PHP-FPMだけでなく、前段のApacheもサービス再起動を行います。

  • Apacheサービス再起動
sudo systemctl restart apache2.service
  • Apacheサービス再起動後確認
systemctl status apache2.service

active(running)を確認します。

  • PHP-FPMサービス再起動
sudo systemctl restart php8.3-fpm.service
  • PHP-FPMサービス再起動後確認
systemctl status php8.3-fpm.service

active(running)を確認します。

事象改善確認

再びNextcloudにアクセスし、事象が改善したことを確認できれば設定完了です。

余談:なぜこの事象が起きたか?

Nextcloudの利用頻度が高まったからに尽きます。Talkをスマートフォンアプリでも利用したり、データが増えたことで、PHP-FPMの処理能力が追いつかなかったのでしょう。

利用状況に合わせて、ボトルネックを特定し、修正を加えて改善を施していくというのもまた、サーバ運用の苦しくも楽しいところです。

BookStack、キャッチ画像の一新。

別で出しているBookStack。(一部の維持は連動しています)

https://barrel.reisalin.com

こちら、nano bananaの画像生勢力により、サイトのイメージを

この状態から

こちらへと変更。このように、ブログとの共通バナーを置いた次第です。

プロンプトは以下の通り
Japanese anime / manga style illustration, (maximum moe-style:1.7), (ultra-detailed:1.6), (dramatic contrast between traditional Japanese study room and holographic terminal commands:1.5), (a giant, aged scroll (Makimono) unrolled, with neon-green shell script flowing across its surface:1.6), (atmospheric illumination from the flowing script and floating "$ " prompts:1.4), (standard lens perspective:1.3), (smooth, natural visual composition:1.2), 16:9, widescreen

THRUST_WEIGHT = 1.7 // Thigh emphasis weight for "Stable Foundation of Automation" (1.5 - 2.0 recommended)

// CORE VARIABLES (Optimized for Shell Script Makimono)
HAIR_COLOR = (Matte, deep charcoal or sleek jet black, styled with elegant, traditional rope braids:1.5) // Traditional yet structured.
HAIR_ACCENT = (Kanzashi designed as a delicate, glowing '$ ' (prompt symbol) icon and a miniature sealing stamp:1.7), (Thin pure white and neon-green braided cord decoration:1.4).
GLASSES_STYLE = (Thin, antique metallic-rimmed glasses, reflecting the complex, flowing script logic:1.6) // Glasses for deep analysis.
OUTFIT_BASE_COLOR = (Structured, deep matte indigo or black Kimono-inspired functional wear:1.5) // Elegant and non-distracting color.
EMBROIDERY_COLOR = Neon-green and vibrant orange (CUI commands and variable names:1.4).
HOSIERY_COLOR = Sheer matte black or opaque deep indigo (smooth, functional texture, with subtle glowing lines resembling command pipes:1.6) // Pipe/Flow lines.

// CONSTRAINT & FOCUS (Filter Mitigation & Execution Focus)
Constraint: (Healthy and dignified, intellectual and deeply focused aesthetic only:1.5), (No offensive or sexually explicit content:1.5), (Focus on automation flow and scripting mastery:1.5).
Focus: (Maximum emphasis on the glowing script text on the scroll:1.8), (Fingers delicately touching the scroll, suggesting script execution:1.6), (The elegant, powerful curve of the upper thighs as a stable base for the command flow:THRUST_WEIGHT).

---

// **LETTERING (Shell Script Title - Execution Command)**
(Large, powerful, and perfectly aligned lettering of the words 'Shell Script' projected as glowing, neon-green commands directly over the center of the unrolled Makimono scroll:1.7), (Strict, mono-spaced terminal font, suggesting code precision and execution integrity:1.5), (The letters feature subtle internal segments that resemble pipe operators '|' and glowing '$' prompt symbols at the start of the word, all in neon green:1.6), (Holographic projection effect with sharp, clean edges and intense neon-green internal illumination, contrasting with the parchment texture:1.5), (Intensely illuminated by its own neon-green light, casting sharp, digital-looking reflections onto the aged parchment and the character's clothing:1.4)

---

// PERSPECTIVE, COMPOSITION, & POSE (Filter Safe & Execution Focus)
Perspective: (Medium-low angle perspective:1.5), emphasizing the grandeur of the unrolled scroll.
Framing: (Full body visible, seated in front of a low, sturdy wooden desk/platform:1.4), (**Framed by the subtle texture of a traditional shoji screen and the ancient wooden desk:1.3**).
PoseAction: (**Seated in a calm, focused posture (正座 or 片膝立ち), both hands gently holding the edges of the unrolled giant Makimono:1.7**), (**One finger or a traditional brush hovering over a glowing line of code, suggesting activation or modification:1.6**). // Scripting/Chanting pose.
Expression: (Intense concentration, a calm yet satisfied gaze as the script logic unfolds:1.5).

---

// SETTING & CYBER DETAILS
Location: (**A quiet, traditional Japanese study room (書斎) with a low, dark wooden desk:1.5**), (**The air is filled with subtle, swirling smoke or vapor, suggesting powerful computation:1.6**).
Decorations: (**A massive, aged parchment scroll unrolled, filled with glowing neon-green and orange shell script commands:1.7**), (**Holographic '$ ' prompts floating in the air like dust motes:1.5**), (A traditional inkstone and brush (筆) resting nearby:1.4).
Atmosphere: (Mysterious, powerful, and deeply focused, the magic of automation:1.2).
Details: (**The intense neon light from the script reflects dramatically off the character's face and the glossy hosiery:1.7**), (The contrast between the fragile parchment/wood and the powerful digital light:1.5).

---

// OUTFIT & ACCESSORIES (Automation Modules)
Outfit: (Kimono-inspired functional scholar's robes:1.4) (base=**OUTFIT_BASE_COLOR**, embroidery color=**EMBROIDERY_COLOR**, motif=flowing script/logic gates), (clean, structured, and matte texture:1.5).
Leg Wear: (**HOSIERY_COLOR** tights/leggings with subtle, pipe-like seams:1.6), (modular thigh strap designed as a scroll tie/seal, with a glowing 'for loop' icon charm:1.5).
Accessories: Minimalist choker designed as a logic gate circuit:1.3, A small, portable, clear glass sphere containing a perfectly ordered 'history' log:1.5.

---

// NEGATIVE PROMPTS (General)
(extra fingers:1.8), (fewer fingers:1.8), (malformed hands:1.8), (extra limbs:1.8), (mutated hands:1.8), (bad anatomy:1.5), (disfigured:1.5), (ugly:1.5), (deformed:1.5), (blurry:1.3), (duplicate:1.3), (morbid:1.2), (mutilated:1.2), (out of frame:1.2), (bad proportion:1.2), (bad quality:1.2), (overly sensual:1.5), (crotch_focus:1.5), (nipples:1.5), (vagina:1.5), (too much skin:1.5).

これで、より、自サイトの統一感が保たせられるようになりました。

PHP-FPMでNextcloudを動作させるための手順。

PHP-FPMを利用したNextcloudのセットアップ方法です。

なぜ mod_php ではなく PHP-FPM を使うのか?

パフォーマンスとリソース効率を向上させるためです。

従来のmod_phpでは、PHPがApacheの全プロセスに組み込まれるため、画像ファイルのリクエストのようなPHPが不要な処理でもメモリを消費し、無駄が多くなりがちでした。

一方、PHP-FPMはPHPの処理をApacheから完全に独立させた専門のプロセスとして管理します。ApacheはPHPが必要なリクエストだけをPHP-FPMに中継するため、サーバー全体の動作が軽量かつ高速になります。

前提

  • OS: Ubuntu 24.04 LTS
    • → SSH接続できること。
    • ※root権限を持っていること。
    • この権限を持っていない場合、ここから先の設定はできません。
  • データベース: MySQL 8.0
  • Webサーバー: Apache 2.4
    • 実行ユーザーはwww-data
    • ホームディレクトリを /home/www-dataにしています。自分の環境に合わせてください。
  • ドメインとSSL/TLS証明書: 準備済みであること

筆者の好みでaptitudeを用いています。必要に応じてaptをご利用ください。

さっくりとはならない手順

  1. リポジトリの追加とアップデートを行います。
  2. パッケージをインストールしていきます。
  3. PHP-FPMの設定を行います。
  4. PHPのパフォーマンス設定を行います。
  5. MySQLでDB設定を行います。
  6. NextcloudのDBを設定します。
  7. Apacheバーチャルホストの設定を行います。
  8. バーチャルホストの設定を有効化します。
  9. 設定の有効化とサービスの再起動を

リポジトリの追加とアップデート

最新のPHPバージョンを利用するためにppa:ondrej/phpリポジトリを追加していきます。

  • レポジトリ追加
sudo add-apt-repository ppa:ondrej/php
  • パッケージ全体のアップデート
sudo apt update

必要なパッケージのインストール

PHP本体、PHP-FPM、Nextcloudが必要とする各種PHPモジュールをインストールします。

sudo aptitude install php8.3 php8.3-fpm php8.3-opcache php8.3-pdo php8.3-bcmath php8.3-calendar php8.3-ctype php8.3-fileinfo php8.3-ftp php8.3-gd php8.3-intl php8.3-json php8.3-mbstring php8.3-mysql php8.3-posix php8.3-readline php8.3-sockets php8.3-bz2 php8.3-tokenizer php8.3-zip php8.3-curl php8.3-iconv php8.3-xml php8.3-imagick php8.3-gmp php8.3-apcu memcached

バージョンを確認します。

php -v

表示例

PHP 8.3.25 (cli) (built: Aug 29 2025 12:01:53) (NTS)
Copyright (c) The PHP Group
Zend Engine v4.3.25, Copyright (c) Zend Technologies
    with Zend OPcache v8.3.25, Copyright (c), by Zend Technologies

PHP-FPMとApacheの連携設定

従来の mod_php を無効化し、PHP-FPMとの通信に必要な proxy_fcgi モジュールなどを有効化します。

  • mod_phpを無効化(もしインストールされていれば)
sudo a2dismod php8.3
  • 必要なモジュールを有効化
sudo a2enmod proxy_fcgi setenvif header rewrite

PHPのパフォーマンス設定

Nextcloudのパフォーマンス向上のため、PHPのメモリ制限、OPcache、APCuを設定します。

  • php.ini の設定 (memory_limit)
sudo sed -i 's/memory_limit = .*/memory_limit = 512M/g' /etc/php/8.3/fpm/php.ini
  • OPcacheとAPCuの有効化

Nextcloud推奨の設定値を /etc/php/8.3/mods-available/ に作成・適用します。

  • OPcache設定
cat <<- __EOF__ | sudo tee /etc/php/8.3/mods-available/opcache.ini
opcache.enable=1
opcache.enable_cli=1
opcache.interned_strings_buffer=16
opcache.max_accelerated_files=10000
opcache.memory_consumption=128
opcache.save_comments=1
opcache.revalidate_freq=1
__EOF__
  • APCu設定
cat <<- __EOF__ | sudo tee /etc/php/8.3/mods-available/apcu.ini
[acpu]
apc.enabled=1
apc.shm_size=32M
apc.ttl=7200 apc.enable_cli=1
apc.serializer=php
__EOF__

データベースの作成

Nextcloudが使用するMySQLデータベースと専用ユーザーを作成します。

  • MySQLにrootでログイン
mysql -u root -p

以下のSQLコマンドを実行します。YOUR_STRONG_PASSWORD は必ず強固なパスワードに変更してください。

CREATE DATABASE IF NOT EXISTS nextcloud CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci;
CREATE USER 'nextcloud'@'localhost' IDENTIFIED WITH mysql_native_password BY 'YOUR_STRONG_PASSWORD';
GRANT ALL PRIVILEGES ON nextcloud.* TO 'nextcloud'@'localhost';
FLUSH PRIVILEGES;
EXIT;

Nextcloudプログラムの配置

Nextcloud本体をダウンロードし、Webサーバーからアクセスできる場所に配置します。

  • 作業ディレクトリへ移動
cd /tmp && pwd

任意のディレクトリを指定します。

  • 最新版をダウンロードして展開
wget https://download.nextcloud.com/server/releases/latest.zip
unzip latest.zip
  • 展開したファイル一式をWeb公開用ディレクトリに移動
sudo mv nextcloud /home/www-data/
  • 所有者をWebサーバーの実行ユーザーに変更
sudo chown -R www-data:www-data /home/www-data/nextcloud

Apacheバーチャルホストの設定

Nextcloud用のApache設定ファイルを作成します。ここでPHP-FPMとの連携設定を組み込みます。

  • ログディレクトリの作成
sudo mkdir /var/log/nextcloud
  • ログディレクトリをwww-dataに修正。

これは、後のメンテナンス性を高めるためです。

sudo chown www-data:www-data /var/log/nextcloud
  • 設定ファイルの作成

/etc/apache2/sites-available/nextcloud.conf

を、teeで一気通貫で作ります。

# 【】内はご自身の環境に合わせてください
cat <<- __EOF__ | sudo tee /etc/apache2/sites-available/nextcloud.conf
<VirtualHost *:80>
    ServerName 【hoge.example.com】
    RewriteEngine On
    RewriteCond %{HTTPS} off
    RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [R=301,L]
</VirtualHost>

<VirtualHost *:443>
    ServerName 【hoge.example.com】
    DocumentRoot 【/home/www-data/nextcloud】

    CustomLog /var/log/nextcloud/nextcloud_access.log combined
    ErrorLog /var/log/nextcloud/nextcloud_error.log

    <Directory 【/home/www-data/nextcloud】>
        Options -MultiViews
        AllowOverride All
        Require all granted
    </Directory>

    # PHP-FPM連携設定
    <FilesMatch \.php$>
        # SetHandlerで、phpファイルのリクエストをPHP-FPMのソケットに渡す
        SetHandler "proxy:unix:/var/run/php/php8.3-fpm.sock|fcgi://localhost/"
    </FilesMatch>

    # --- SSL設定 ---
    SSLEngine on
    Protocols h2 http/1.1
    SSLCertificateFile 【/etc/certs/hoge.example.com.crt】
    SSLCertificateKeyFile 【/etc/private/hoge.example.com.key】
    # 中間証明書が別に提供されている場合はこちらを有効化
    # SSLCACertificateFile 【/etc/certs/hoge.example.com.CA.crt】

    # --- 推奨SSL/TLS設定 ---
    SSLProtocol             all -SSLv3 -TLSv1 -TLSv1.1
    SSLCipherSuite          ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384
    SSLHonorCipherOrder     on
    SSLCompression          off
    SSLSessionTickets       off

    # --- セキュリティヘッダー ---
    # Header always set Strict-Transport-Security "max-age=15552000; includeSubDomains"
    Header always set Referrer-Policy "no-referrer"
    Header always set X-Content-Type-Options "nosniff"
    Header always set X-Frame-Options "SAMEORIGIN"
    Header always set X-Permitted-Cross-Domain-Policies "none"
</VirtualHost>
__EOF__

設定の有効化とサービスの再起動

  • 作成したサイト設定を有効化
sudo a2ensite nextcloud.conf
  • 構文チェック
sudo apache2ctl configtest

Syntax OK と表示されることを確認

  • fpm/apacheサービスを再起動
sudo systemctl restart php8.3-fpm.service
sudo systemctl restart apache2.service
  • fpm/apache再起動確認
systemctl status php8.3-fpm.service
systemctl status apache2.service

active (running)と表示されていれば正常です。

Webブラウザでのセットアップ

最後に、Webブラウザで https://【設定したドメイン】 にアクセスし、画面の指示に従ってNextcloudの初期設定を完了させます。

  • 管理者ユーザーのユーザー名とパスワードを入力
  • データベース情報を入力
    • データベースのユーザー名: nextcloud
    • データベースのパスワード: 手順5で設定したパスワード
    • データベース名: nextcloud
    • データベースのホスト名: localhost (または localhost:3306)

これで、PHP-FPM上で動作するNextcloud環境の構築が完了します。

Page 1 of 53

Powered by WordPress & Theme by Anders Norén