再利用コンポーネントのレンダーコンテキストをリセットして漏洩を防止
ViewComponent 4.12.0 では、同一コンポーネントインスタンスを複数回レンダーした際に残留していた レンダーコンテキスト が原因でデータが漏れる問題を修正しました。今回のリリースはバージョン番号の更新に加えて、核心的なバグ修正とそれに伴うテスト・ドキュメントの整備が行われています。
背景
レンダーコンテキストの残留 が過去のバージョンで報告され、同一インスタンスを再利用したときに前回リクエストのコントローラやヘルパー情報が次回のレンダーに流出するリスクがありました。Issue #(該当なし)で指摘されたケースでは、ユーザー情報やリクエストスコープが誤って共有され、セキュリティ上の懸念が生じていました。
この問題を根本的に解決するには、コンポーネントが #render_in を呼び出すたびに 内部の ivar(@__vc_original_view_context など)をリセットし、常に現在のビューコンテキストを取得させる必要があります。
技術的な変更
コアロジックの修正
@@
- options.set_original_view_context(self.__vc_original_view_context)
+ options.set_original_view_context(__vc_original_view_context)
この差分は、self を介さずにプライベートメソッド __vc_original_view_context を直接参照するよう変更した点です。self を付与すると、メソッド検索がレシーバーオブジェクトに対して行われ、期待したコンテキストが取得できないケースがありました。直接呼び出すことで、インスタンス固有のビューコンテキストが正しく渡されます。
バージョン情報の更新
@@
- MINOR = 11
+ MINOR = 12
マイナーバージョンが 4.12.0 に更新され、リリース番号とドキュメントが整合しました。
テストの期待値調整
レンダーコンテキストリセットに伴い、メモリ割り当て測定の期待範囲が微調整されています。変更箇所は test/sandbox/test/rendering_test.rb で、assert_allocations の期待値が 1〜2 行ずつ増加しています。これにより、修正後のパフォーマンス基準が新しい実装にマッチします。
ドキュメントとメタデータの更新
-
docs/CHANGELOG.mdに「Fix stale render context on reused component instances」のエントリが追加され、修正内容が明示されました。 -
docs/_data/library.ymlと各gemfiles/*.gemfile.lockがバージョン 4.12.0 に合わせて更新され、依存関係ロックファイルにもmini_portile2・nokogiri等の最新版が取り込まれました。
影響範囲
コード変更は 1 行だけで、既存の #render_in 呼び出し側の API には影響しません。従来 true/false のフラグ使用はそのまま動作し、内部リセットロジックだけが新たに有効になります。
設計判断
コンテキストリセットを #render_in の内部で行う 方針は、コンポーネントインスタンスの再利用を前提とした設計に合致します。変更は最小限のコード差分で実装され、後方互換性を保持しつつセキュリティとデータ分離を強化しました。self を除外した直接呼び出しは、Ruby のメソッドディスパッチコストを増やさずに可読性を向上させる選択です。
この判断により、開発者はコンポーネントをキャッシュや再利用しても、リクエストごとに正しいビューコンテキストが保証されます。