Python 的 urljoin:告别手动拼接 URL 的烦恼

📌 前言

在日常爬虫、API 调用或 Web 开发中,我们经常需要拼接 URL。

比如基础地址是 https://example.com/api/,后面要加上 user/info,最终得到
https://example.com/api/user/info

很多新手会直接用 +f-string 来拼接,但这样很容易少写或多写斜杠,导致 URL 错误。

Python 标准库 urllib.parse 提供了一个非常方便的函数 ------ urljoin ,它能智能地拼接 URL,帮你自动处理斜杠问题。


🎯 作用一句话概括

urljoin(base, url) 将基础地址 base 和相对路径 url 拼接成一个完整、合法的绝对 URL。


📖 基本用法

复制代码
from urllib.parse import urljoin

base = "https://www.example.com"
relative = "login/"

full_url = urljoin(base, relative)
print(full_url)

输出:

复制代码
https://www.example.com/login/

瞧,它自动在 comlogin 之间加上了 /,完美!


🧪 几个简单的例子

✅ 例子 1:基础地址末尾有斜杠

复制代码
base = "https://example.com/"
relative = "api/user"
print(urljoin(base, relative))   # https://example.com/api/user

✅ 例子 2:基础地址末尾没有斜杠

复制代码
base = "https://example.com"
relative = "api/user"
print(urljoin(base, relative))   # https://example.com/api/user

注意:和例子 1 结果一样,urljoin 会自动补充斜杠,不用担心!

✅ 例子 3:相对路径以斜杠开头

复制代码
base = "https://example.com/abc/"
relative = "/login/"
print(urljoin(base, relative))   # https://example.com/login/

如果 relative/ 开头,它会替换掉整个路径部分,只保留协议和域名。

✅ 例子 4:相对路径是上一级目录

复制代码
base = "https://example.com/user/profile/"
relative = "../settings/"
print(urljoin(base, relative))   # https://example.com/user/settings/

urljoin 也支持 Unix 风格的相对路径 (...)。

✅ 例子 5:相对路径是一个完整的 URL

复制代码
base = "https://example.com"
relative = "https://google.com/search"
print(urljoin(base, relative))   # https://google.com/search

如果 relative 已经是一个完整的绝对 URL,urljoin直接返回它 ,忽略 base

✅ 例子 6:仅追加path

复制代码
base = "https://example.com/abc/"
relative = "login"

print(urljoin(base,relative)) # https://example.com/abc/login

可以封装成函数使用

复制代码
from urllib.parse import urljoin

def urljoin_test(base, relative):
    # rstrip('/'):去掉 base_url 末尾的斜杠,防止后面手动加 / 时出现双斜杠。
    base = base.rstrip('/')
    # base_url + '/':保证基础部分以 / 结尾。
    # path.lstrip('/'):去掉 path 开头的斜杠,保证中间只有一个 /。
    # 最后 urljoin 做最终的拼接,安全可靠。
    url = urljoin(base + '/', relative.lstrip('/'))
    return url

base = "https://example.com/abc/"
relative = "/login"

print(urljoin_test(base,relative))  # https://example.com/abc/login

如果把 relative 改成不以 / 开头,这时就会在原有路径后面追加 login/,而不是替换。


🚫 手动拼接有什么坑?

假设你想拼接 https://ex.com/api/v1/users

复制代码
# 错误示范 ❌
base = "https://ex.com/api"
bad_url = base + "/v1/users"   # 结果:https://ex.com/api/v1/users  (看起来对?)

好像没问题?但换个场景就出问题:

复制代码
base = "https://ex.com/api/"   # 末尾多了一个斜杠
bad_url = base + "/v1/users"   # 结果:https://ex.com/api//v1/users (两个斜杠!)

虽然浏览器有时能容忍双斜杠,但这不是规范的 URL,某些严格的服务端会报错。

urljoin 永远不会出现双斜杠:

复制代码
from urllib.parse import urljoin
base = "https://ex.com/api/"
print(urljoin(base, "/v1/users"))  # https://ex.com/api/v1/users ✅

💡 实际应用场景

场景 说明
爬虫 从 HTML 中提取 href="/news/123",与当前页面 URL 拼接成绝对链接
API 客户端 基础地址 https://api.example.com/v1,动态拼接 users, posts 等端点
Django/Flask 测试 测试中动态构建请求 URL
配置文件 配置一个 base_url,各处调用 urljoin 拼接子路径

📝 代码模板(直接复制用)

复制代码
from urllib.parse import urljoin

class ApiClient:
    def __init__(self, base_url):
        self.base_url = base_url.rstrip('/')  # 去掉末尾斜杠,urljoin 会自动加

    def _url(self, path):
        return urljoin(self.base_url + '/', path.lstrip('/'))

    def get_users(self):
        full_url = self._url("/users")
        print(f"请求地址: {full_url}")
        # 这里发请求...

client = ApiClient("https://myapi.com")
client.get_users()   # 输出: 请求地址: https://myapi.com/users

⚠️ 注意事项(新手常见疑问)

  1. urljoin 不会做网络请求,它只负责字符串拼接。

  2. 第二个参数以 // 开头 时(例如 //example.com/),会沿用原协议(http 或 https),但这种行为很多新手可能想不到,尽量避免这样用。

  3. 第二个参数以 ?# 开头时,会替换原 URL 的查询参数或锚点。

  4. 如果需要处理非常规 URL(比如 file:///C:/test),urljoin 也能工作。


🎓 总结

方法 是否智能处理斜杠 是否支持 .. 路径 推荐程度
手动 + 不推荐
f-string 不推荐
os.path.join ❌(用于文件路径,不是 URL) 不推荐
urljoin ✅ 强烈推荐

一句话记住:以后拼接 URL,直接用 urljoin,别再手动加斜杠了!


🔍 扩展阅读

相关推荐
嵌入式小企鹅2 分钟前
UiPath推出AI编程“总指挥台”,SiFive发布RISC-V第三代猛兽
人工智能·学习·google·程序员·ai编程·risc-v·开源工具
Ada大侦探16 分钟前
新手小白学习数据分析03----Excel 报表之大厂周报(2026最新版实操,包教包会!)
学习·数据分析·excel
-To be number.wan1 小时前
进程与线程的区别
学习·操作系统
llhm2 小时前
tsp学习笔记——LINUX SDK编译2(2)Kernel6.1 Linux
linux·笔记·学习
李白不吃坚果3 小时前
沟道电荷的思考
学习·cmos·集成电路·模拟集成电路设计·沟道电荷
学会870上岸华师4 小时前
C 语言程序设计——第一章课后编程题
c语言·开发语言·学习·算法
nashane4 小时前
HarmonyOS 6学习:AI攻略长截图“防抖”与像素级拼接术
学习·华为·harmonyos
wangcheng3035 小时前
关键词优化怎么理解最清楚
笔记
吃好睡好便好5 小时前
在Matlab中绘制三维等高线图
开发语言·python·学习·算法·matlab·信息可视化
土星碎冰机6 小时前
ai自学笔记(3.安卓篇,制作app
android·笔记·ai