Django+HTMX社交加好友系统CSRF Token无效致403错误求助
Django + HTMX 好友系统 403 Forbidden(无效CSRF Token)问题解决方案
核心问题分析
Django的CSRF保护机制要求所有POST请求必须携带有效CSRF Token,你的代码中虽尝试通过hx-headers传递Token,但存在局部模板Token渲染失效、请求未覆盖目标UI更新、冗余Token设置等问题,导致Token验证失败触发403错误。
具体修复步骤
1. 全局配置HTMX自动携带CSRF Token
避免每个按钮重复编写hx-headers,同时解决局部模板无法获取csrf_token的问题:
在base.html的<body>末尾添加以下脚本,并确保页面包含CSRF Token字段:
<!-- 在base.html中添加CSRF隐藏字段 --> {% csrf_token %} <!-- HTMX全局配置:自动携带CSRF Token --> <script> document.body.addEventListener('htmx:configRequest', (event) => { event.detail.headers['X-CSRFToken'] = document.querySelector('[name=csrfmiddlewaretoken]').value; }); </script>
添加后,所有HTMX POST请求会自动携带有效Token,无需在按钮上单独设置hx-headers。
2. 修复sent_requests.html中的变量错误
模板中按钮的id使用了未定义的user变量,导致渲染异常,修改为:
<button id="cancel-{{ request.requests_user.username }}" hx-post="{% url 'cancel_request' request.pk %}" hx-trigger="click" hx-target="#sent-requests" hx-swap="innerHTML" class="p-3 bg-red-100 hover:bg-red-200 rounded-lg text-red-800 font-bold flex gap-2 items-center" > <i class="fa-solid fa-xmark text-lg"></i> Cancel Request </button>
3. 修复add_friend视图的UI更新逻辑
当前视图仅更新已发送请求列表,未实现“添加好友后移除对应用户”的需求,使用HTMX的OOB(Out of Band)交换同时更新两个区域:
def add_friend(request, username): user_to_request = User.objects.get(username=username) # 创建好友请求 Friend.objects.create(user=request.user, requests_user=user_to_request) # 获取最新的已发送请求和无关系用户列表 sent_requests = Friend.objects.filter(user=request.user, request_accepted=False) users = get_users_no_rel(request.user) # 生成两个区域的HTML内容 add_friend_html = render_to_string( 'base/partials/add_friends.html', {'user_list': users}, request=request # 确保模板能获取上下文 ) sent_requests_html = render_to_string( "base/partials/sent_requests.html", {'sent_requests': sent_requests}, request=request ) # 组合OOB响应,同时更新#sent-requests和#add区域 response_html = f""" {sent_requests_html} <div id="add" hx-swap-oob="outerHTML">{add_friend_html}</div> """ return HttpResponse(response_html)
4. 移除冗余的Token设置
cancel_request视图中手动设置X-CSRFToken响应头是多余的,Django会自动管理CSRF Cookie,删除以下代码:
# response['X-CSRFToken'] = get_token(request) # 移除该行
验证步骤
- 打开浏览器开发者工具的Network标签;
- 触发添加/取消好友请求,检查POST请求的Headers中是否包含
X-CSRFToken字段,且值与页面中csrfmiddlewaretoken隐藏字段一致; - 确认操作后,
#add区域的用户列表和#sent-requests区域的请求列表均正确更新。
内容的提问来源于stack exchange,提问作者Chinyere Unamba
相关产品推荐
相关产品推荐

