Django中redirect能否传递两个变量?动态URL配置问题
Django动态URL传递两个变量的问题排查
问题场景
我尝试在Django中创建包含两个变量的动态URL,urls.py配置如下:
path('fin-data-add/<str:fintype>/fin-data-update/<str:pk>', views.finDataUpdate, name='fin-data-update'), path('fin-data-add/\<str:fintype\>/fin-data-delete/\<str:pk\>', views.finDataDelete, name='fin-data-delete') path('fin-data-add/\<str:fintype\>/fin-categories/fin-categories-delete/\<str:pk\>', views.finCatDelete, name='fin-categories-delete')
在views.py中处理逻辑并传递变量:
@login_required(login_url='home:login') def finDataUpdate(request, fintype, pk): expense = Expenses.objects.get(id=pk) form = ExpenseForm(instance=expense) if request.method == 'POST': form = ExpenseForm(request.POST, instance=expense) if form.is_valid(): obj = form.save(commit=False) obj.user = request.user obj.save() return redirect('boost:fin-data-update', kwargs={'fintype': fintype, 'pk': pk}) database = Expenses.objects.all() fin_type = 'Expense' fin_type_plural = 'Expenses' context = {'form': form, 'database': database, 'fin_type': fin_type, 'fin_type_plural': fin_type_plural} return render(request, 'boost/fin-data-update.html', context)
运行后出现错误:
NoReverseMatch at /boost/fin-data-add/expense Reverse for 'fin-data-update' with arguments '(45,)' not found. 1 pattern(s) tried: ['boost/fin\\-data\\-add/(?P<fintype>[^/]+)/fin\\-data\\-update/(?P<pk>[^/]+)\\Z']
问题解答
完全可以通过动态URL传递两个变量,你的错误来自反向解析参数不全和URL配置的语法错误,具体修复步骤如下:
1. 修正urls.py的语法错误
- 不需要转义
<和>,直接写<str:变量名>即可; - 确保每个path末尾的逗号(最后一行除外);
- 去掉path开头的多余空格。
修正后的urls.py:
path('fin-data-add/<str:fintype>/fin-data-update/<str:pk>', views.finDataUpdate, name='fin-data-update'), path('fin-data-add/<str:fintype>/fin-data-delete/<str:pk>', views.finDataDelete, name='fin-data-delete'), path('fin-data-add/<str:fintype>/fin-categories/fin-categories-delete/<str:pk>', views.finCatDelete, name='fin-categories-delete')
2. 补全反向解析的参数
错误提示显示反向解析时只传了一个参数(45,)(也就是pk),但URL需要fintype和pk两个参数。这个问题大概率出在模板中的URL调用:
如果模板里写了类似下面的代码,就会报错:
{% url 'boost:fin-data-update' pk=object.pk %}
必须同时传递两个参数,正确写法:
{% url 'boost:fin-data-update' fintype=fintype pk=object.pk %}
3. views.py的优化建议
- 用
get_object_or_404替代直接get,避免pk不存在时抛出服务器错误:from django.shortcuts import get_object_or_404 expense = get_object_or_404(Expenses, id=pk, user=request.user) - 可以用传入的
fintype参数动态生成页面标题,避免写死:fin_type = fintype.capitalize() fin_type_plural = f'{fin_type}s'
内容的提问来源于stack exchange,提问作者Gustavo Santos de Paula
相关产品推荐
相关产品推荐

