JavaScript

How to parse a query string in JavaScript.

The modern answer is URLSearchParams — it decodes values for you, handles repeated keys, and is built into every browser and Node.js. Here’s how to use it, plus the edge cases (arrays, + vs %20, nested objects) that trip people up.

The short answer

Use the built-in URLSearchParams. It parses a query string into key/value pairs and decodes each value automatically:

const params = new URLSearchParams('?q=hello world&page=2');
params.get('q');     // "hello world"  (decoded)
params.get('page');  // "2"
params.has('page');  // true

You can build it from location.search in the browser to read the current page’s query string:

const params = new URLSearchParams(location.search);
const query = params.get('q');

Repeated keys: use getAll

Query strings can repeat a key — ?tag=js&tag=url is two values for tag. get() returns only the first; getAll() returns every value:

const params = new URLSearchParams('tag=js&tag=url&tag=web');
params.get('tag');     // "js"          (first only)
params.getAll('tag');  // ["js","url","web"]

Loop over every parameter

for (const [key, value] of params) {
  console.log(key, '=', value);
}

Convert to a plain object

Object.fromEntries is the quick way — but note it collapses repeated keys to the last value, so only use it when keys are unique:

const obj = Object.fromEntries(new URLSearchParams('a=1&b=2'));
// { a: "1", b: "2" }

// Repeated keys need manual handling:
const params = new URLSearchParams('tag=js&tag=url');
const grouped = {};
for (const [k, v] of params) {
  grouped[k] = grouped[k] ? [...[].concat(grouped[k]), v] : v;
}
// { tag: ["js","url"] }

+ vs %20 (an important gotcha)

In a query string, + means a space (a form-encoding convention), and URLSearchParams decodes it as such. In a path, + is a literal plus. So parsing ?q=a+b gives "a b", which is usually what you want — but if your data legitimately contains a plus, it must arrive as %2B.

new URLSearchParams('q=a+b').get('q');    // "a b"
new URLSearchParams('q=a%2Bb').get('q');  // "a+b"  (literal plus)

Parse a full URL, not just the query

If you have a whole URL, let the URL object split it first, then read .searchParams:

const url = new URL('https://example.com/search?q=hello&page=2');
url.searchParams.get('q');  // "hello"
url.pathname;               // "/search"

Want to see this visually? Paste any URL into our query string parser or URL parser to see every parameter decoded in a table.

About this page

Written and maintained by the urlencodedecode.com team. Every technical claim on this page is verified against primary sources — the RFCs (3986, 3629, 4648, 7578), the WHATWG URL Standard, and official vendor or language documentation — rather than second-hand summaries. When a source contradicts a common assumption, we follow the source and note the discrepancy. Corrections: contactus@urlencodedecode.com.

Common questions

Frequently asked.

Use the built-in URLSearchParams: new URLSearchParams(location.search). Call .get(key) for a single value, .getAll(key) for repeated keys, and iterate with for...of to read every pair. Values are decoded automatically.

Use params.getAll('tag'), which returns an array of all values ["a","b"]. The plain params.get('tag') returns only the first value, and Object.fromEntries collapses duplicates to the last value.

In a query string, + is the form-encoded representation of a space (application/x-www-form-urlencoded), and URLSearchParams decodes it to a space. If you need a literal plus in a value, it must be encoded as %2B.

Yes. URLSearchParams is a global in modern Node.js (and available via the 'url' module in older versions), so the same code works server-side without any dependency.

Object.fromEntries(new URLSearchParams(str)) gives a plain object for unique keys. For query strings with repeated keys, loop with for...of and group the values into arrays yourself, since Object.fromEntries keeps only the last value per key.

Related

Keep exploring.