Python
URL encoding
percent-encoding
URL parameters
web development

How can I percent-encode URL parameters in Python?

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

In Python, the correct tool for percent-encoding URL parameters is usually urllib.parse.urlencode. It handles query strings safely, escapes reserved characters, and avoids the common mistake of trying to build URLs with manual string concatenation.

The important detail is that URL encoding depends on context. Query parameters, path segments, and entire URLs are not encoded the same way, so using the right function matters.

Encode Query Parameters with urlencode

If you have key-value parameters for a query string, use urlencode:

python
1from urllib.parse import urlencode
2
3params = {
4    "q": "red shoes",
5    "category": "men/winter",
6    "page": 2,
7}
8
9query_string = urlencode(params)
10print(query_string)

Output:

text
q=red+shoes&category=men%2Fwinter&page=2

Spaces become + by default because query strings commonly use form-style encoding. Reserved characters such as / are escaped when they appear inside parameter values.

To build a full URL:

python
base_url = "https://example.com/search"
full_url = f"{base_url}?{query_string}"
print(full_url)

Repeated Parameters with doseq=True

If a parameter can appear multiple times, pass a list and enable doseq=True:

python
1from urllib.parse import urlencode
2
3params = {
4    "tag": ["python", "urllib", "encoding"],
5    "sort": "recent",
6}
7
8query_string = urlencode(params, doseq=True)
9print(query_string)

Output:

text
tag=python&tag=urllib&tag=encoding&sort=recent

Without doseq=True, the list would be encoded as a single string representation, which is usually not what APIs expect.

quote vs quote_plus

If you need to encode one value manually rather than a full dictionary, use quote or quote_plus.

python
1from urllib.parse import quote, quote_plus
2
3value = "red shoes & socks"
4
5print(quote(value))
6print(quote_plus(value))

Output:

text
red%20shoes%20%26%20socks
red+shoes+%26+socks

Use quote_plus for query parameter values when + for spaces is acceptable. Use quote when you specifically want %20.

Query Parameters Are Not Path Segments

One common bug is using urlencode for a URL path. Query parameters and path segments follow different expectations.

For a path segment, use quote:

python
1from urllib.parse import quote
2
3username = "Jane Doe/QA"
4safe_path = quote(username, safe="")
5print(safe_path)

Output:

text
Jane%20Doe%2FQA

If you leave / in the safe set, it will remain a slash and split the path unexpectedly.

Full Example with requests

If you are using requests, you often do not need to call urlencode yourself. Pass the params argument and let the library encode it:

python
1import requests
2
3params = {
4    "q": "red shoes",
5    "size": "10",
6}
7
8response = requests.get("https://httpbin.org/get", params=params, timeout=10)
9print(response.url)

This is safer than concatenating the query string by hand and easier to maintain.

Unicode and Non-ASCII Characters

Percent-encoding also handles Unicode safely by first encoding characters as UTF-8 bytes.

python
1from urllib.parse import urlencode
2
3params = {"city": "Montréal", "emoji": "☕"}
4print(urlencode(params))

Output looks like:

text
city=Montr%C3%A9al&emoji=%E2%98%95

That is normal and correct. URLs carry the encoded byte representation, not raw Unicode characters in every context.

Common Pitfalls

The biggest pitfall is building query strings with string interpolation. That breaks as soon as a value contains spaces, ampersands, slashes, or non-ASCII characters.

Another mistake is using quote on an entire key=value&key2=value2 string. That usually over-encodes separators and produces a broken query string. Encode the individual values or use urlencode on the whole parameter mapping.

Developers also forget doseq=True for repeated parameters. Many web APIs expect repeated keys, not a Python list literal encoded into a string.

Finally, do not confuse query encoding with path encoding. urlencode is for query strings; quote is for path segments and other individual URL components.

Summary

  • Use urllib.parse.urlencode for query parameter dictionaries.
  • Use doseq=True when parameter values are lists that should expand into repeated keys.
  • Use quote or quote_plus for individual values when needed.
  • Query strings and path segments should not be encoded with the same helper blindly.
  • Avoid manual string concatenation for URLs.
  • Libraries like requests can often handle parameter encoding for you automatically.

Course illustration
Course illustration

All Rights Reserved.