title: How to update the URL of a page without causing a reload using vanilla JavaScript
url: https://gomakethings.com/how-to-update-the-url-of-a-page-without-causing-a-reload-using-vanilla-javascript/
hash_url: 2c67b87e1b880952bb277fc429cb8bf5

<p>Yesterday, we looked at <a href="https://gomakethings.com/how-to-create-a-search-page-for-a-static-website-with-vanilla-js/">how to build a vanilla JavaScript search feature for a static website</a>. At the end, I mentioned…</p>

<blockquote>
<p>Tomorrow, I’ll show you how I update the URL with the search query, and run a search automatically on page load if there’s a query in the URL.</p>
</blockquote>

<p>Well, today is tomorrow, so let’s dig in!</p>

<p><em><strong>Note:</strong> If you haven’t yet, you should probably read yesterday’s post first, or today’s won’t make much sense.</em></p>

<h2 id="updating-the-url">Updating the URL</h2>

<p>In our <code>search()</code> function, we create an array of regex patterns, get an array of matching items (sorted by how many matches they have), and then render them into the UI.</p>

<p>Let’s create another function, <code>updateURL()</code>, to update the URL for us. We’ll pass in the search <code>query</code> as an argument.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="cm">/**
</span><span class="cm"> * Search for matches
</span><span class="cm"> * @param  {String} query The term to search for
</span><span class="cm"> */</span>
<span class="kd">function</span> <span class="nx">search</span> <span class="p">(</span><span class="nx">query</span><span class="p">)</span> <span class="p">{</span>

	<span class="c1">// ...
</span><span class="c1"></span>
	<span class="c1">// Display the results
</span><span class="c1"></span>	<span class="nx">showResults</span><span class="p">(</span><span class="nx">results</span><span class="p">);</span>

	<span class="c1">// Update the URL
</span><span class="c1"></span>	<span class="nx">updateURL</span><span class="p">(</span><span class="nx">query</span><span class="p">);</span>

<span class="p">}</span>
</code></pre></div>
<p>We’re going to use <a href="https://gomakethings.com/how-to-update-the-browser-url-without-refreshing-the-page-using-the-vanilla-js-history-api/">the <code>history.pushState()</code> method</a> to update our URL.</p>

<p>This creates a new entry in the browser’s history (and updates the URL) <em>without</em> causing the page to reload. It accepts three arguments: the browser <code>state</code>, a <code>title</code> to use in the <code>document</code>, and the <code>url</code>.</p>

<p>We’ll use the current <code>history.state</code>, no need to replace anything. We’ll also use the current <code>document.title</code>.</p>

<p>For the <code>url</code>, we’ll combine the <code>location.origin</code> and <code>location.pathname</code>, then append the <code>?s</code> query string parameter, and use the <code>query</code> for its value. We’ll pass the <code>query</code> into the <code>encodeURI()</code> method to encode it.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="cm">/**
</span><span class="cm"> * Update the URL with a query string for the search string
</span><span class="cm"> * @param  {String} query The search query
</span><span class="cm"> */</span>
<span class="kd">function</span> <span class="nx">updateURL</span> <span class="p">(</span><span class="nx">query</span><span class="p">)</span> <span class="p">{</span>

	<span class="c1">// Create the properties
</span><span class="c1"></span>	<span class="kd">let</span> <span class="nx">state</span> <span class="o">=</span> <span class="nx">history</span><span class="p">.</span><span class="nx">state</span><span class="p">;</span>
	<span class="kd">let</span> <span class="nx">title</span> <span class="o">=</span> <span class="nb">document</span><span class="p">.</span><span class="nx">title</span><span class="p">;</span>
	<span class="kd">let</span> <span class="nx">url</span> <span class="o">=</span> <span class="nb">window</span><span class="p">.</span><span class="nx">location</span><span class="p">.</span><span class="nx">origin</span> <span class="o">+</span> <span class="nb">window</span><span class="p">.</span><span class="nx">location</span><span class="p">.</span><span class="nx">pathname</span> <span class="o">+</span> <span class="s1">'?s='</span> <span class="o">+</span> <span class="nb">encodeURI</span><span class="p">(</span><span class="nx">query</span><span class="p">);</span>

<span class="p">}</span>
</code></pre></div>
<p>Finally, we can pass all three into the <code>history.pushState()</code> method to update the URL.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="cm">/**
</span><span class="cm"> * Update the URL with a query string for the search string
</span><span class="cm"> * @param  {String} query The search query
</span><span class="cm"> */</span>
<span class="kd">function</span> <span class="nx">updateURL</span> <span class="p">(</span><span class="nx">query</span><span class="p">)</span> <span class="p">{</span>

	<span class="c1">// Create the properties
</span><span class="c1"></span>	<span class="c1">// ...
</span><span class="c1"></span>
	<span class="c1">// Update the URL
</span><span class="c1"></span>	<span class="nx">history</span><span class="p">.</span><span class="nx">pushState</span><span class="p">(</span><span class="nx">state</span><span class="p">,</span> <span class="nx">title</span><span class="p">,</span> <span class="nx">url</span><span class="p">);</span>

<span class="p">}</span>
</code></pre></div>
<h2 id="running-a-search-on-page-load">Running a search on page load</h2>

<p>If the URL has an <code>s</code> query string parameter when the page loads, we should also run a search immediately. This lets users bookmark search pages for later.</p>

<p>First, we’ll create an <code>onload()</code> function to run immediately with the script.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="c1">// Create a submit handler
</span><span class="c1"></span><span class="nx">form</span><span class="p">.</span><span class="nx">addEventListener</span><span class="p">(</span><span class="s1">'submit'</span><span class="p">,</span> <span class="nx">submitHandler</span><span class="p">);</span>

<span class="c1">// Check for query strings onload
</span><span class="c1"></span><span class="nx">onload</span><span class="p">();</span>
</code></pre></div>
<p>We’ll use <a href="https://gomakethings.com/getting-values-from-a-url-with-vanilla-js/">the <code>new URLSearchParams()</code> constructor</a> to create a <code>URLSearchParams</code> object from the <code>location.search</code> property.</p>

<p>Then, we’ll use the <code>URLSearchParams.get()</code> method to look for a query string parameter with a key of <code>s</code>.</p>

<p>If one is <em>not</em> found, we’ll use the <code>return</code> operator to end our function.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="cm">/**
</span><span class="cm"> * If there's a query string search term, search it on page load
</span><span class="cm"> */</span>
<span class="kd">function</span> <span class="nx">onload</span> <span class="p">()</span> <span class="p">{</span>
	<span class="kd">let</span> <span class="nx">query</span> <span class="o">=</span> <span class="k">new</span> <span class="nx">URLSearchParams</span><span class="p">(</span><span class="nb">window</span><span class="p">.</span><span class="nx">location</span><span class="p">.</span><span class="nx">search</span><span class="p">).</span><span class="nx">get</span><span class="p">(</span><span class="s1">'s'</span><span class="p">);</span>
	<span class="k">if</span> <span class="p">(</span><span class="o">!</span><span class="nx">query</span><span class="p">)</span> <span class="k">return</span><span class="p">;</span>
<span class="p">}</span>
</code></pre></div>
<p>If a <code>query</code> exists, we’ll update the <code>input.value</code> property with it so that the search field contains the search <code>query</code>. Then, we’ll pass the <code>query</code> into the <code>search()</code> function to run a search.</p>

<p>The <code>URLSearchParams.get()</code> method automatically decodes the parameter for us, so we don’t need to worry about that.</p>
<div class="highlight"><pre class="chroma"><code class="language-js" data-lang="js"><span class="cm">/**
</span><span class="cm"> * If there's a query string search term, search it on page load
</span><span class="cm"> */</span>
<span class="kd">function</span> <span class="nx">onload</span> <span class="p">()</span> <span class="p">{</span>
	<span class="kd">let</span> <span class="nx">query</span> <span class="o">=</span> <span class="k">new</span> <span class="nx">URLSearchParams</span><span class="p">(</span><span class="nb">window</span><span class="p">.</span><span class="nx">location</span><span class="p">.</span><span class="nx">search</span><span class="p">).</span><span class="nx">get</span><span class="p">(</span><span class="s1">'s'</span><span class="p">);</span>
	<span class="k">if</span> <span class="p">(</span><span class="o">!</span><span class="nx">query</span><span class="p">)</span> <span class="k">return</span><span class="p">;</span>
	<span class="nx">input</span><span class="p">.</span><span class="nx">value</span> <span class="o">=</span> <span class="nx">query</span><span class="p">;</span>
	<span class="nx">search</span><span class="p">(</span><span class="nx">query</span><span class="p">);</span>
<span class="p">}</span>
</code></pre></div>
<p>Now, when someone reloads or revists a search page, a new search will automatically run.</p>
