Ruby ランタイム

Ruby ランタイムは、アプリケーション コードと依存関係をインストールして、フレキシブル環境でそのアプリケーションを実行する役割を果たすソフトウェア スタックです。

  • バージョン 3.2 以降は Buildpack を使用してビルドされているため、app.yaml ファイルでオペレーティング システムを選択する必要があります。たとえば、Ruby 3.3(プレビュー版)を使用するには、オペレーティング システムとして Ubuntu 22 を指定する必要があります。

  • バージョン 3.1 以前は Docker を使用してビルドされています。

サポートされている Ruby のバージョンと、それに対応する Ubuntu のバージョンの完全なリストについては、ランタイム サポート スケジュールをご覧ください。

Ruby のバージョン

Ruby バージョン 3.2 以降の場合は、app.yaml ファイルに runtime_configoperating_system の設定を追加して、オペレーティング システムを指定する必要があります。

Ruby 3.3(プレビュー版)を使用するには、次のことを行う必要があります。

  • Gemfile で Ruby のバージョンを指定します。

    RUBY VERSION
      ruby 3.3.x
    
  • gcloud CLI バージョン 420.0.0 以降をインストールします。CLI ツールを更新するには、gcloud components update コマンドを実行します。インストールされているバージョンを表示するには、gcloud version コマンドを実行します。

  • app.yaml ファイルで operating_system 設定を指定します。

      runtime: ruby
      env: flex
    
      runtime_config:
          operating_system: "ubuntu22"
    
  • 必要に応じて、アプリケーション ディレクトリの .ruby-version ファイルを使用して、Ruby インタープリタのバージョンを指定できます。例: 3.3.x

以前のバージョン

Ruby ランタイム バージョン 3.1 以前の場合は、アプリケーション ディレクトリの .ruby-version ファイルを使用して Ruby インタープリタのバージョンを指定します。

このファイルが存在する場合、アプリケーションをデプロイすると、ランタイムが rbenv を使用して要求されたバージョンの Ruby をインストールします。要求されたバージョンをインストールできない場合、デプロイ中に App Engine によりエラー メッセージが表示されます。

.ruby-version ファイルを指定しない場合、Ruby ランタイムはデフォルトでバージョン 2.7 になります。デフォルトはいつでも変更できますので、アプリで Ruby バージョンを指定することをおすすめします。

他の Ruby ランタイムのサポート

カスタム ランタイムを使用すると、App Engine フレキシブル環境で動作する Ruby アプリに機能を追加できます。カスタム ランタイムを構成するには、app.yaml ファイルの次の行を置き換えます。

runtime: ruby

これを次のように変更します。

runtime: custom

また、app.yaml ファイルのある同じディレクトリに Dockerfile ファイルと .dockerignore ファイルを追加する必要があります。詳細については、カスタム ランタイムをご覧ください。

依存関係

ランタイムは、アプリケーションの起動前にアプリケーションのソース ディレクトリで Gemfile ファイルを探し、Bundler を使用して依存関係をインストールします。パッケージの宣言と管理の詳細については、Ruby ライブラリの使用をご覧ください。

Ruby での C ライブラリの使用

C 拡張を必要とする Ruby ライブラリの場合は、現在の Ruby バージョンと次の Ubuntu パッケージのヘッダーがシステムにプリインストールされています。

  • autoconf
  • build-essential
  • ca-certificates
  • cmake
  • curl
  • file
  • git
  • imagemagick
  • libcurl3
  • libcurl3-gnutls
  • libcurl4-openssl-dev
  • libffi-dev
  • libgdbm-dev
  • libgit2-dev
  • libgmp-dev
  • libicu-dev
  • libjemalloc-dev
  • libjemalloc1
  • libmagickwand-dev
  • libmysqlclient-dev
  • libncurses5-dev
  • libpq-dev
  • libqdbm-dev
  • libreadline6-dev
  • libsqlite3-dev
  • libssl-dev
  • libxml2-dev
  • libxslt-dev
  • libyaml-dev
  • libz-dev
  • systemtap
  • tzdata

これらのパッケージを使用すると、よく利用されている Ruby ライブラリをインストールできます。アプリケーションで追加のオペレーティング システムレベルの依存関係が必要な場合は、このランタイムに基づいてカスタム ランタイムを使用し、適切なパッケージをインストールする必要があります。

アプリケーションの起動

ランタイムは、app.yaml で定義された entrypoint を使用してアプリケーションを起動します。エントリ ポイントは、環境変数 PORT で定義されたポートで HTTP リクエストのレスポンス処理を開始する必要があります。例:

entrypoint: bundle exec rails server -p $PORT

大部分のウェブ アプリケーションは、PumaUnicornThin など、Rack 対応のウェブサーバーを使用します。

アプリケーションの Gemfile 構成ファイルにサーバーを依存関係として追加する必要があります。ランタイムは、エントリポイントが呼び出される前にすべての依存関係をインストールします。

source "https://rubygems.org"

gem "rack"
gem "puma"

Rails アプリケーションで puma を使用したエントリ ポイントの例:

entrypoint: bundle exec rails server Puma -p $PORT

Rack アプリケーションで puma を使用したエントリ ポイントの例:

entrypoint: bundle exec rackup -s Puma -p $PORT

Rack サーバーなしでリクエストを処理できるアプリケーションの場合には、Ruby スクリプトを実行します。

entrypoint: bundle exec ruby app.rb

環境変数

次の環境変数が、ランタイム環境によって設定されます。

環境変数 説明
GAE_INSTANCE 現在のインスタンスの名前。
GAE_MEMORY_MB アプリケーション プロセスで使用可能なメモリ量。
GAE_SERVICE アプリケーションの app.yaml ファイルで指定されたサービス名。サービス名が指定されていない場合は、default に設定されます。
GAE_VERSION 現在のアプリケーションのバージョン ラベル。
GOOGLE_CLOUD_PROJECT アプリケーションに関連付けられたプロジェクト ID。この ID は、Google Cloud Console に表示されます。
PORT HTTP リクエストを受信するポート。
RACK_ENV production に設定します。
RAILS_ENV production に設定します。
RAILS_SERVE_STATIC_FILES true に設定します。

app.yaml で、追加の構成変数を設定できます。

メタデータ サーバー

アプリケーションの各インスタンスは、ホスト名、外部 IP アドレス、インスタンス ID、カスタム メタデータ、サービス アカウント情報など、インスタンスに関する情報を Compute Engine メタデータ サーバーから取得します。App Engine では、インスタンスごとにカスタム メタデータを設定することはできませんが、プロジェクト単位のカスタム メタデータを設定して、App Engine インスタンスや Compute Engine インスタンスから読み取ることができます。

このサンプル関数では、メタデータ サーバーから、Ruby ランタイム バージョン 3.1 以前を実行しているインスタンスと 3.3 以降を実行しているインスタンスの外部 IP アドレスを取得します。新しいバージョンを使用するには app.yaml ファイルを更新する必要があることに留意してください。新しいランタイムの使用の詳細については、Ruby ランタイムをご覧ください。

require "sinatra"
require "net/http"

get "/" do
  uri = URI.parse(
    "http://metadata.google.internal/computeMetadata/v1"  
    "/instance/network-interfaces/0/access-configs/0/external-ip"
  )

  request = Net::HTTP::Get.new uri.path
  request.add_field "Metadata-Flavor", "Google"

  http = Net::HTTP.new uri.host, uri.port

  response = http.request request

  "External IP: #{response.body}"
end