当我尝试渲染视图时,收到一条错误消息“ / manifest处的KeyError”。我是第一次使用会话,因此不确定如何解决此问题。我正在尝试使用会话将字段“引用”从edit_manifest_frombrowse
视图传递到manifest
视图。有人可以向我解释是什么导致了此错误,为什么我可以修复它?代码和完整的回溯如下:
views.py
def edit_manifest_frombrowse(request, pk):
item = get_object_or_404(Manifests, pk=pk)
if request.method == "POST":
form = CreateManifestForm(request.POST, instance=item)
if form.is_valid():
request.session["reference"] = form.cleaned_data["reference"]
return redirect('manifest')
else:
form = CreateManifestForm(instance=item)
return render(request, 'edit_manifest_frombrowse.html', {'form': form})
def manifest(request):
form = CreateManifestForm(request.POST)
if request.method == "POST":
...
reference_id = request.session.pop('reference', None)
data = Manifests.objects.all().filter(reference__reference=reference_id)
form = CreateManifestForm(initial={
'reference': Orders.objects.get(reference=reference_id),
})
total_cases = Manifests.objects.filter(reference__reference=reference_id).aggregate(Sum('cases'))
context = {
'reference_id': reference_id,
'form': form,
'data': data,
'total_cases': total_cases['cases__sum'],
}
return render(request, 'manifest_readonly.html', context)
forms.py
class CreateManifestForm(forms.ModelForm):
class Meta:
model = Manifests
fields = ('reference', 'cases', 'product_name', 'count', 'CNF', 'FOB')
models.py
#form which I am trying to submit
class Manifests(models.Model):
reference = models.ForeignKey(Orders)
#just showing so you can see what the FK reference
class Orders(models.Model):
reference = models.CharField(max_length=50, unique=True)
完整的回溯
Request Method: GET
Request URL: http://127.0.0.1:8000/manifest
Django Version: 1.11
Python Version: 2.7.10
Installed Applications:
['django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'django.contrib.humanize',
'bootstrap_modal_forms',
'smart_selects',
'unit']
Installed Middleware:
['django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware']
Traceback:
File "/Library/Python/2.7/site-packages/django/core/handlers/exception.py" in inner
41. response = get_response(request)
File "/Library/Python/2.7/site-packages/django/core/handlers/base.py" in _get_response
187. response = self.process_exception_by_middleware(e, request)
File "/Library/Python/2.7/site-packages/django/core/handlers/base.py" in _get_response
185. response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/Users/andrews/Desktop/WBU/web_unit/unit/views.py" in manifest
325. reference_id = request.session.pop('reference')
File "/Library/Python/2.7/site-packages/django/contrib/sessions/backends/base.py" in pop
73. return self._session.pop(key, *args)
Exception Type: KeyError at /manifest
Exception Value: 'reference'
答案 0 :(得分:0)
您收到此错误,是因为这是pop方法的行为。
pop(key [,default]):如果key在字典中,请将其删除并返回其值,否则返回default。如果未提供默认值并且字典中没有key,则会引发KeyError。
因此,要解决此问题,您可以使用后备方法摆脱此错误。例如:
reference_id = request.session.pop("reference", None)
您的逻辑问题可能是导致您遇到此错误的根本原因。
if form.is_valid():
request.session["reference"] = form.cleaned_data["reference"]
return redirect('manifest')
如果您的表单无效,则会话变量上将没有reference
,因此您将无法在manifest
视图中获取它。因此,尝试重定向到另一个视图或尝试执行以下操作:
if form.is_valid():
# Do other stuff
request.session["reference"] = form.cleaned_data["reference"]
else:
# Do other stuff
request.session["reference"] = ""
return redirect('manifest')
当您要使用查询集启动时,表单存在另一个问题。它将尝试将您的Orders查询集解析为表单的类似JSON的数据,这将提示错误。您应该尝试为reference
字段创建替代字段,并在 init 方法上为该字段设置查询集,如下所示:
# forms.py
class CreateManifestForm(forms.ModelForm):
reference = forms.ModelChoiceField(queryset=Orders.objects.none())
class Meta:
model = Manifests
fields = ('reference', 'cases', 'product_name', 'count', 'CNF', 'FOB')
def __init__(self, reference, *args, **kwargs):
super(CreateManifestForm, self).__init__(*args, **kwargs)
self.fields['reference'].queryset = reference
然后您可以像这样初始化表格:
form = CreateManifestForm(reference=Orders.objects.filter(reference=reference_id))
希望有帮助!