13
4

More than 1 year has passed since last update.

scriptタグに指定するnonceについて

Posted at

ある日、開発で使用しているgemのlayoutファイルに以下のようなコードを見かけました。

<%= javascript_tag nonce: true do %>

javascript_tagnonce: trueのオプションが渡されています。
「なんぞこれ?」となったのでとりあえずnonceに関して調べてみました。

nonceについて

scriptタグに付与することができるnonce属性は、XSS攻撃などで不正なスクリプトが実行されることを防ぐために利用されます。

nonceは"number used once"の略で、一度だけ使用される数値を意味しています。
scriptタグに設定されたnonce属性には以下のような使い捨ての乱数を設定し、ページを読み込むたびに異なる乱数が再設定されるようにします。

<script nonce="8IBTHwOdqNKAWeKl7plt8g==">
  // …
</script>

さらに、nonceに設定した乱数と同じ値をContent-Security-Policyヘッダーで送信するようにします。
そうすることでContent-Security-Policyヘッダーに設定されたnonce値が設定されたscriptのみを実行対象とし、正規のnonce値を持たないscriptは実行されなくなります。

Content-Security-Policy: script-src 'nonce-8IBTHwOdqNKAWeKl7plt8g=='

Railsでnonceを使う

Railsでnonceを利用したい場合は以下の設定をconfig/initializers/content_security_policy.rbに記載します。

config/initializers/content_security_policy.rb
Rails.application.config.content_security_policy do |policy|
  policy.script_src :self, :https
end

Rails.application.config.content_security_policy_nonce_generator = -> request { SecureRandom.base64(16) }

これで以下のようにjavascript_tagnonce: tureを渡せばnonce値が自動的に追加され、実行されるスクリプトを制限することができるようになります。

<%= javascript_tag nonce: true do -%>
  alert('Hello, World!');
<% end -%>

ちなみに以下のメソッドでnonceに設定されている乱数を取得することもできます。

request.content_security_policy_nonce
=> "3xdpMsDFBsRpwY8KQp//LQ=="

13
4
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
13
4