手動のセットアップや一貫性に欠けるデプロイワークフローは排除されつつある、今日のWordPress開発。RadicleはRootsBedrockSageAcornなどのWordPress開発ツールを単一のスタータースタックに統合してくれます。

つまり、Radicleを導入すれば、WordPressで直接Laravelの開発経験を実現することができます。

Kinstaでは、SSH接続WP-CLI統合ドキュメントルートの設定が可能なため、Radicleに必要な技術的要件を満たしています。

そこで今回は、Kinstaのインフラストラクチャ上でRadicleを動作させるために必要な設定プロセスとデプロイ手順をご紹介します。

Radicleとそのコンポーネント

Radicleは、以下3つの異なるRootsプロジェクトを統合した開発環境です。

  • Bedrock:改善されたフォルダ構造とComposerベースの依存関係管理で基盤を提供
  • SageTailwind CSS統合とアセット構築用のViteでテーマ開発に対応
  • AcornBladeテンプレート、マイグレーション、ルーティングなどをWordPressプロジェクトに取り込む、WordPressとLaravelの橋渡し役

このタイプの開発環境では、一般的なテーマディレクトリ内ではなく、プロジェクトルートから直接作業することが可能です。テンプレートはプロジェクトルートのresources/views/、構成はbedrockディレクトリの環境固有のファイルを通して行われます。

Composerは、WordPressのコア、プラグイン、およびカスタムの依存関係を単一のcomposer.jsonファイルで管理します。このスタックには、PHP 8.3以上と特定の拡張機能が必要です。また、依存関係の管理にはComposer、コマンドライン操作にはWP-CLIが必要になります。

Radicleと従来のWordPressの違い

標準的なWordPressの構成(wp-contentディレクトリ内にすべて配置)では、バージョン管理が複雑になり、異なる環境間で一貫した構成の維持が難しくなります。

Radicleではこれを再構築し、WordPressのコアファイルやアップロードされたメディアを追跡することなく、アプリケーションコードをバージョン管理することができます。

  • WordPressコアは、アプリケーションコードとは別にpublic/wpディレクトリに配置
  • public/contentディレクトリはwp-contentを置き換え、カスタムテーマのコードはプロジェクトルートに配置

Laravelスタイルの構成は、構成ファイル内にデータベース認証情報やセキュリティキーを埋め込むのではなく、.envファイルを使用します。開発環境、ステージング環境、本番環境で異なる設定bedrock/environments/にある個別の設定ファイルで定義します。

また、アプリケーションのコードと構成だけを追跡するため、バージョン管理戦略にもメリットがあります。WordPressコアの更新はComposerを通じて行われ、プラグインは依存関係として機能し、テーマの変更はリポジトリに保存されます。

Kinsta用にRadicleを設定する

Kinstaにデプロイする際は、MyKinstaで利用できるSSHキー認証が必要です。

サイトの「情報」画面で「メインSFTP/SSHユーザー」セクションの詳細を確認し、なければ公開SSHキーを追加します。

MyKinstaののSSH/SFTP情報
MyKinstaののSSH/SFTP情報

KinstaのインフラはRadicleの技術要件を満たしており、PHP 8.3対応、依存関係管理用のComposerが含まれているほか、WP-CLIもあらかじめインストールされており、コマンドラインから直接WordPressを操作可能です。

従来のWordPress構成とは異なり、Radicleはリリースベースのディレクトリ構造を採用しています。そのため、各配備はタイムスタンプ付きのリリースフォルダを作成し、currentシンボリックリンクは、アクティブなバージョンを指します。また、アプリケーションのウェブルートはpublic/current/publicに設定する必要があります。

次に環境変数を設定します。Radicleプロジェクトルートにある.env.exampleファイルをコピーし、名前を.envに変更します。続いて、データベースの詳細と環境設定を追加します。

DB_NAME='your_database_name'
DB_USER='your_database_user'
DB_PASSWORD='your_database_password'
DB_HOST='your_database_host'
WP_ENV='staging'
WP_HOME='https://{kinsta-staging-url}'
WP_SITEURL="${WP_HOME}/wp"

WordPressコアは、/wpサブディレクトリ内にインストールされます。これにより、コアファイルはカスタムアプリケーションのコードから分離され、よりクリーンでバージョン管理された構造になります。

ステージング設定

設定ディレクトリはpublicresourcesフォルダともに、Radicleプロジェクトのルートにあります。bedrock/environments/staging.phpを開いて、ステージング環境に固有の設定を定義します。.envファイルがWP_ENVstagingに設定するたび、このファイルがbedrock/application.phpの値を上書きします。

staging.phpの先頭に以下の定数を追加して、ステージング環境のURLを設定してください。

<?php
define('WP_HOME', 'https://staging-url');
define('WP_SITEURL', WP_HOME . '/wp');

ステージングURLは、ステージング環境を選択する際、サイトの「環境」セクションのパターンに従います。

MyKinstaでステージング環境のURLを見つける
MyKinstaでステージング環境のURLを見つける

設定した配置先のパスによって、Kinstaサーバー上のどこにファイルが置かれるかが決まります。MyKinsta の「環境情報」セクションに表示されているパスを確認してください。通常は/www/sitename/publicのように表示され、これがファイルを配置する場所になります。配置用のスクリプトはこの場所にファイルを同期し、/www/sitename/public/releases/timestampといった形で配置ごとにフォルダを作り、/www/sitename/public/currentが現在有効なリリース(公開中のバージョン)を指すように設定されます。

また、bedrock/environments/staging.phpでステージング環境のデバッグモードを有効にすることをおすすめします。さらに、ステージング環境のデータベース認証情報をローカルの.envファイルにコピーして設定します(バージョン管理にはコミットしない)。または、これらをデプロイメントサーバーの環境変数として設定します。Kinstaは各環境に対して一意の認証情報を生成します。

本番環境設定

MyKinstaのドロップダウンメニューから本番環境に切り替えると、設定プロセスはステージング環境を反映しますが、本番環境固有の値と厳しいセキュリティ設定を使用します。

これを行うには、プロジェクトルートのbedrockディレクトリでbedrock/environments/production.phpを開き、本番用URLを修正します。

<?php
define('WP_HOME', 'https://yourdomain.com');
define('WP_SITEURL', WP_HOME . '/wp');

本番環境でのエラー処理はステージング環境とは異なり、エラーログを維持したまま、デバッグ表示を無効にします。

define('WP_DEBUG', false);
define('WP_DEBUG_LOG', true);
define('WP_DEBUG_DISPLAY', false);
define('SCRIPT_DEBUG', false); 

さらに、本番環境にいる状態で、MyKinstaの「データベースへのアクセス」セクションから本番用データベースの接続情報をコピーします。これらの情報はステージングとは通常異なります。ただし、本番環境の配置パスはステージングと同じ形式に従うものの、本番用のディレクトリを指す点が異なります。MyKinstaの「環境情報」に表示されるパスも、似てはいるものの別のURLになっているはずです。配置用スクリプトは、このパスを本番環境へのリリース先として利用します。

デプロイタスクの変更

Radicle標準のデプロイメント設定は、Kinstaのマネージドサーバーでは提供されていないサーバー操作が可能であることを前提にしています。そのため、サーバーのサービスを操作しようとするデプロイメントタスクはすべて削除する必要があります。

Trellis(Radicle のデフォルトデプロイメントツール)を使用している場合は、trellis/roles/deploy/hooks/finalize-after.ymlを編集し、Reload php-fpmタスクを完全に削除してください。Kinstaでは、ファイルの変更を検出するとPHP-FPMが自動的に再起動されます。

また、キャッシュクリアはサーバーコマンドではなくKinsta APIを通じて行われるため、サーバーベースのキャッシュクリアをKinstaのキャッシュクリアエンドポイントへのHTTPリクエストに置き換える必要があります。APIキーを設定したら、このタスクをデプロイのfinalizeフックに追加します。

- name: Kinstaキャッシュのクリア
uri:
  url: "{{ site_env.wp_home }}/kinsta-clear-cache-endpoint/"
  method: GET

セキュリティ上、各サイトには固有のエンドポイントがあります。これはカスタマーサポートから取得可能です。

アセットコンパイルはサーバー上ではなく、デプロイの前に実行されます。ローカルの開発マシンまたはCI/CDパイプラインは、npm run build、JavaScriptとCSSをpublic/buildディレクトリにコンパイルします。これらのコンパイルされたアセットは、PHPファイルと一緒にデプロイされます。

Composerの依存関係のインストールは、SSHを使用してファイルを同期した後に以下を実行します。

cd /www/sitename/public/current
composer install --no-dev --optimize-autoloader --no-interaction

--no-devフラグは、テストフレームワークやデバッグツールのような開発用の依存関係を除外します。--optimize-autoloaderフラグは、自動読み込みを高速化するためにクラスマップを構築し、リクエスト中にクラスファイルを検索するオーバーヘッドを削減します。

RadicleにKinsta MUプラグインを追加する

Kinsta MUプラグインは、MyKinstaを通じてサイトのフルページキャッシュ、CDN統合、キャッシュ管理を可能にします。Radicleのディレクトリ構造は非標準のため、いくつかの特定の設定定数を設定する必要がありますが、Composerから追加できます。プラグインをインストールした後、これらの定数をbedrock/application.phpファイルに追加します。

/**
* Radicle/Bedrock構成でのKinsta CDN修正
*/

define('KINSTA_CDN_USERDIRS', 'app');

/**
* Radicle/Bedrock環境でのKinsta MUプラグインのURLパス修正
*/

$mu_plugins_url = Config::get('WP_CONTENT_URL') . '/mu-plugins';

define('KINSTAMU_CUSTOM_MUPLUGIN_URL', "{$mu_plugins_url}/kinsta-mu-plugins");

最初の定数は、Bedrockのapp構造でアップロードディレクトリを指定します。2つ目の定数は、プラグインのアセットURLパスを修正し、JavaScriptとCSSファイルを正しく読み込むようにします。

プラグインをインストールしたら、MyKinstaからキャッシュのクリアを実行し、プラグインがKinstaのインフラと正しく通信できているかを確認してください。

自動デプロイを設定する

GitHub Actionsを使用すると、簡単にRadicleのKinstaへのデプロイを自動化することができます。例えば、.github/workflows/deploy.ymlのリポジトリにワークフローファイルを作成します。このワークフローは、特定のブランチへのプッシュをトリガーとしてアセットをビルドし、対応する環境にコードをデプロイします。

GitHub リポジトリにSSH用のシークレットを設定しておくと、Kinstaサーバーへ安全に接続できるようになります。これには、SSHの秘密鍵、Kinstaのホスト名、SSHポート、そしてユーザー名といった情報をGitHubのシークレットとして追加しておきましょう。

デプロイメント用のスクリプトは、ファイルを同期する一連の処理をまとめて実行する役割を担います。一般的に、このスクリプトはrsyncを使って効率よくファイルを転送し、変更されたファイルだけを送り、必要な権限も維持します。ただし、本番環境をクリーンに保つために、node_modules.git.envといった開発用のファイルはデプロイ対象から除外しておくことをおすすめします。

ファイルの同期が正しく完了すると、キャッシュ削除や後処理のタスクを実行できるようになります。具体的には、デプロイメントスクリプトが Kinstaのキャッシュクリア用エンドポイントにリクエストを送り、その完了を待ってから、必要なクリーンアップ処理を実行するという流れになります。

GitHub Actionsの設定

.github/workflows/deploy.ymlファイルを作成して、リポジトリのルート内でデプロイの自動化を定義することができます。これはアセットのコンパイル、依存関係のインストール、Kinstaへのファイルの同期を処理します。

まずは、ステージングブランチをステージング環境にデプロイし、mainブランチを本番環境にデプロイするブランチ固有のトリガーを行います。

name: Kinstaへのデプロイ
on:
push:
branches:
  - staging
  - main
jobs:
deploy:
runs-on: ubuntu-latest
steps:
  - name: コードのチェック
    uses: actions/checkout@v3
  - name: Node.jsのセットアップ
    uses: actions/setup-node@v3
    with:
      node-version: '22'
  - name: 依存関係のインストールとアセットのビルド
    run: |
      npm ci
      npm run build

GitHub Actionsのmatrix機能を使うと、ワークフローのコードを重複させることなく複数の環境をまとめて扱えるようになります。設定した環境ごとの変数は、どのブランチでワークフローが実行されたかによって切り替わります。

strategy:
  matrix:
    include:
      - branch: staging
        ssh_host: ${{ secrets.KINSTA_STAGING_HOST }}
        ssh_port: ${{ secrets.KINSTA_STAGING_PORT }}
        ssh_user: ${{ secrets.KINSTA_STAGING_USER }}
        deploy_path: /www/sitename_1/public
      - branch: main
        ssh_host: ${{ secrets.KINSTA_PRODUCTION_HOST }}
        ssh_port: ${{ secrets.KINSTA_PRODUCTION_PORT }}
        ssh_user: ${{ secrets.KINSTA_PRODUCTION_USER }}
        deploy_path: /www/sitename_2/public

アセットコンパイルステップは、デプロイ前に最適化されたJavaScriptとCSS ファイルを作成します。ワークフローはnpm installの代わりにnpm ciを使用し、package-lock.jsonファイルに基づいて再現可能なビルドを行います。npm run buildコマンドは、package.jsonで定義された本番ビルドスクリプトを実行します。通常、Viteか他のバンドラーを実行し、アセットのコンパイルと圧縮を行います。

ここまで準備できたら、Node.jsの処理ステップの後にComposerのインストール処理を追加します。

- name: PHPのセットアップ
  uses: server/setup-php@v2
  with:
    php-version: '8.3'

  - name: Composerの依存関係をインストール
    run: composer install --no-dev --optimize-autoloader --no-interaction

これで、ワークフローはKinstaへのデプロイに必要なコンパイル済みアセットと依存関係をすべて準備できた状態になります。

デプロイスクリプトの詳細

rsyncを介したファイルの同期は、変更されたファイルのみを転送し、デプロイ時間を最小限に抑えます。これを解決するには、アセットをビルドした後、GitHub Actionsワークフローにこのステップを追加します。

- name: rsyncを使ってKinstaにデプロイ
  env:
    SSH_PRIVATE_KEY: ${{ secrets.SSH_PRIVATE_KEY }}
  run: |
    mkdir -p ~/.ssh
    echo "$SSH_PRIVATE_KEY" > ~/.ssh/deploy_key
    chmod 600 ~/.ssh/deploy_key
    rsync -avz --delete 
      --exclude='.git' 
      --exclude='node_modules' 
      --exclude='.env' 
      --exclude='trellis' 
      -e "ssh -i ~/.ssh/deploy_key -p ${{ matrix.ssh_port }} -o StrictHostKeyChecking=no" 
      ./ ${{ matrix.ssh_user }}@${{ matrix.ssh_host }}:${{ matrix.deploy_path }}/releases/$(date +%Y%m%d%H%M%S)/

rsyncフラグは転送の動作を制御します。

  • -a:アーカイブモードを有効にし、パーミッションやタイムスタンプを保持
  • -v:詳細なログを出力し、デバッグに役立つ
  • -z:転送中のデータを圧縮

--deleteフラグは、リポジトリに存在しないファイルをサーバーから削除し、デプロイメントをクリーンに保ちます。

Excludeパターンが不要なファイルの転送を防ぎます。さらに、Gitメタデータ、開発用依存ファイル、環境ファイル、デプロイメントツールは本番サーバーに残りません。リリースディレクトリ構造により、デプロイメントごとにタイムスタンプ付きのディレクトリが作成され、シンボリックリンクを変更することで迅速なロールバックが可能になります。

シンボリックリンク管理は、永続データを各新規リリースに接続します。ファイルを同期した後、SSHでサーバにログインしてシンボリックリンクを作成できます。

- name: シンボリックリンクを作成してcurrentを更新
  run: |
    ssh -i ~/.ssh/deploy_key -p ${{ matrix.ssh_port }} -o StrictHostKeyChecking=no 
      ${{ matrix.ssh_user }}@${{ matrix.ssh_host }} << 'EOF'
    cd ${{ matrix.deploy_path }}
    # Link shared .env file
    ln -nfs ${{ matrix.deploy_path }}/shared/.env 
      ${{ matrix.deploy_path }}/releases/$(ls -t releases | head -1)/.env
    # Link uploads directory
    ln -nfs ${{ matrix.deploy_path }}/shared/public/content/uploads 
      ${{ matrix.deploy_path }}/releases/$(ls -t releases | head -1)/public/content/uploads
    # Update current symlink atomically
    ln -nfs ${{ matrix.deploy_path }}/releases/$(ls -t releases | head -1) 
      ${{ matrix.deploy_path }}/current
    EOF

.envファイルには環境ごとの設定が含まれており、デプロイをまたいでも保持されます。リリースディレクトリの外側にアップロードファイルを置いておくことで、古いリリースが削除されてもメディアが失われることはありません。また、シンボリックリンクを一瞬で安全に切り替える(ln -nfsを使う)ことで、処理途中のリリースが参照されることがなく、ダウンなしで切り替えが行えます。

クリーンナップは、デプロイに成功した後に古いリリースを削除し、最新の5つだけを残します。

- name: 古いリリースの整理
  run: |
    ssh -i ~/.ssh/deploy_key -p ${{ matrix.ssh_port }} -o StrictHostKeyChecking=no 
      ${{ matrix.ssh_user }}@${{ matrix.ssh_host }} << 'EOF'
    cd ${{ matrix.deploy_path }}/releases
    ls -t | tail -n +6 | xargs rm -rf
    EOF

このクリーンアップ方法は、ディスク容量の節約とロールバックの柔軟性のちょうどよいバランスを保ちます。5つのリリースを残しておけば、十分なロールバックポイントを確保しつつ、保存が際限なく増え続けるのを防げます。

まとめ

Radicleは、Bedrockの整理されたディレクトリ構造、Sageのモダンなテーマ開発ワークフロー、そしてAcornがもたらすLaravelの機能を1つのスタックにまとめることで、WordPress開発のあり方を大きく変えてくれます。

Kinstaへのデプロイには、一般的なWordPress用サーバー以上の設定が必要になりますが、その分、セキュリティ、保守性、そして開発体験の面で大きなメリットが得られるため、手間に十分見合う価値があります。

最新のWordPressアプリケーションを安心してデプロイするなら、KinstaのWordPress専用マネージドサーバーをぜひお試しください。カスタム開発ワークフローをしっかり支えるサーバー環境を手にすることができます。

Joel Olawanle Kinsta

Kinstaでテクニカルエディターとして働くフロントエンド開発者。オープンソースをこよなく愛する講師でもあり、JavaScriptとそのフレームワークを中心に200件以上の技術記事を執筆している。