はじめに
今年(2017年)の4月末にRuby on Rails (Rails)のバージョン5.1がリリースされましたが、わずか7ヵ月後の11月末に早くもバージョン5.2のベータ版がリリースされています。
Rails 5.1が、Webpack / Yarnのサポートなどフロントエンドの新機能を中心としたリリースだったのに対し、Rails 5.2は、ファイルアップロード用のActive Storageなどバックエンドの新機能を中心としたリリースになるようです。
本記事では、GitHubのRailsプロジェクトのIssuesやPull Requestsの履歴、Railsの公式ブログの記事をもとに、Rails 5.2の主要な新機能について、まとめています。
※ 他のバージョンのRailsの主要な新機能・機能追加・変更点については以下を参照してください。
- 今から知っておきたいRails 5の新機能・変更点 - Qiita
- ReactやwebpackもサポートしたRails 5.1の新機能・変更点 - Qiita
- Ruby on Rails 6の主要な新機能・機能追加・変更点
Active Storage
Active Storageはファイルアップロードの新機能で、以前から利用されてきたPaperclipやCarrierwaveなどのサードパーティのGemの代わりとなるものです。
アップロード・参照先としては、Amazon S3, Google Cloud Storage, Microsoft Azure Blob Storageなどのクラウドサービスを標準で利用することができ、また、ダイレクトアップロードという、ブラウザから直接クラウドサービスへアップロードできる機能や、ミラーリング機能を備えます。
アップロードするファイルが画像の場合はオンデマンドでサイズの変換(MiniMagickを使用)が可能であり、動画やPDFの場合はプレビューを生成することが可能です。どのファイルの場合も、メタデータの取得はジョブによって非同期で行われます。
Railsアプリケーションから使用する場合は、以下のコマンドを実行し、ファイル情報と関連づけの格納に必要なテーブルをDBに作成します。
$ bin/rails active_storage:install
$ bin/rails db:migrate
ファイル情報と関連づけに使用するモデルは以下のようになっています。
(各モデルは、ActiveStorageの内部で定義されており、実装し直す必要はありません。)
-
Blob
- ファイル情報(Content-Type、サイズ、クラウドでの識別用のkeyやメタデータなど)を格納
-
Attachment
- ファイルと他のモデルとの関連づけ用の中間テーブル
Railsアプリケーション側のモデルからは、以下のようにhas_many_attached
メソッドを使用します。以下はArticle
モデルにimages
という名前で複数のファイルをアップロードする場合の例です。
class Article < ApplicationRecord
has_many_attached :images
単一のファイルをアップロードする場合は、has_one_attached
メソッドを使用します。
class Article < ApplicationRecord
has_one_attached :image
その他の詳細な内容や各クラウドへアップロードする場合の設定に関しては、公式のドキュメントや、こちらのスライドを参照してください。
Redisキャッシュストア
Railsではこれまでメモリ、ファイル、Memcachedを利用したキャッシュ機構を提供していましたが、これに加えて、Redisを利用したキャッシュ機構を提供するようになりました。
Redisへのキャッシュは使われてから最も長い時間が経ったもの、参照される頻度が最も低いものを優先的に無効にします。
(Rails 5.2ではキャッシュのキーの再利用・圧縮も行われるようになったので、Redisによるキャッシュと組み合わせると、以前より高い効率でのキャッシュが可能になりました。)
標準ではキャッシュの読み書きに失敗した場合は、例外でなくnil
(キャッシュにヒットしなかった)とみなすので、設定を正しく行えばこれまでのアプリケーションと変わりなく使用することができます。
Redisのバックエンドとしては、redis Gemだけでなく、hiredisやRedis::Distributedをサポートします。
Railsアプリケーションで利用するには、各環境の設定ファイルで以下のように設定を行います。
# config/environments/production.rb
config.cache_store = :redis_cache_store
より詳しい内容(各バックエンドを利用する方法など)については、公式ドキュメントを参照してください。
HTTP/2 Early Hints
Early Hintsは、Webサーバーにリクエストが完了する前にヘッダで必要なJavaScriptやスタイルシート(アセット)のURLを伝えることができ、より高速なページの表示を可能にします。
RFC 8297のAn HTTP Status Code for Indicating Hints によると、最初にステータス103でLinkヘッダにアセットのURLを埋め込んだレスポンスを返し、次に実際のボディと同じLinkヘッダを含むレスポンスを返します。アセットの各ファイルはサーバーからHTTP/2 Server Pushによってクライアントに送信されます。
HTTP/1.1 103 Early Hints
Link: </style.css>; rel=preload; as=style
Link: </script.js>; rel=preload; as=script
HTTP/1.1 200 OK
Date: Fri, 26 May 2017 10:02:11 GMT
Content-Length: 1234
Content-Type: text/html; charset=utf-8
Link: </style.css>; rel=preload; as=style
Link: </script.js>; rel=preload; as=script
Railsでは、HTTPのLinkヘッダに、javascript_include_tag
/ stylesheet_link_tag
に記述されたファイルのURLを埋め込みます。
使用するには、h2oとpumaの新しいバージョン(3.11.0以上)のセットアップを行った後に、bin/rails s
に--early-hints
オプションをつけて起動します。
Bootsnap
Bootsnapと呼ばれるRailsアプリケーションの起動時間を短縮するライブラリが、Gemfile
に含まれるようになりました。
Bootsnapのサイトによると起動時間が半分程度になるそうです。
Content Security Policy
Content Security Policy (CSP)は、サーバーがHTTPヘッダにContent-Security-Policy
の内容を含むレスポンスを返すことで、ブラウザ側でクロスサイトスクリプティング(XSS)やパケット盗聴攻撃を防ぐ仕組みのことです。
Rails 5.2ではサードパーティのGem(secureheadersなど)を使用しなくても、CSPの設定が簡単にでき、セキュリティを強化できるようになりました。
RailsアプリケーションでCSPを設定するには、config/initializers/content_security_policy.rb
で以下のように設定します。
Rails.application.config.content_security_policy do |policy|
policy.default_src :self, :https # サイト自身のドメインとHTTPSを使用した全ドメイン
policy.style_src :self, :https, :unsafe_inline # インラインの<style>要素を許可(危険)
...
end
コントローラで設定をカスタマイズするには、content_security_policy
メソッドを使用します。
class ArticlesController < ApplicationController
content_security_policy do |policy|
policy.upgrade_insecure_requests true # httpをhttpsへリダイレクト(対応ブラウザの場合)
end
end
- Add DSL for configuring Content-Security-Policy header #31162
- Content Security Policy (CSP) - Web セキュリティ | MDN
暗号化されたCredentials
これまで、複数存在していたRailsアプリケーション内の機密情報(config/secrets.yml
や、SECRET_BASE_KEY
)を1つのファイル(config/credentials.yml.enc
)内に暗号化して格納できるようになりました。
(これによって、Rails 5.1で導入された、encrypted secretsも置き換えられてしまいました。)
ファイルの復号には、環境変数RAILS_MASTER_KEY
を使用し、bin/rails credentials:edit
コマンドで内容を編集を行うことができます。
config/credentials.yml.enc
の中身は例えば、以下のようになっています。
aws:
access_key_id: XXXXXXXXXXXXXXXX
secret_access_key: XXXXXXXXXXXXXXXXXXX
# Used as the base secret for all MessageVerifiers in Rails, including the one protecting cookies.
secret_key_base: XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
ファイルを保存すると、自動的に再度暗号化されます。
まとめ
Rails 5.2はファイルアップロードを簡単に行えるActive StorageやRedisキャッシュストアなど、バックエンド周りの新機能を追加したバージョンとなるようです。
また、Content Security Policyの設定や暗号化されたCredentialsの管理も可能になっており、よりセキュアなアプリケーションの構築が可能になっています。
来年のリリースに向けて、新機能を試してみたり、既存のアプリケーションのアップグレードをしてみてはいかがでしょうか。