Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/json/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Django 如果包含模型,如何序列化已清理的_数据?_Django_Json_Serialization - Fatal编程技术网

Django 如果包含模型,如何序列化已清理的_数据?

Django 如果包含模型,如何序列化已清理的_数据?,django,json,serialization,Django,Json,Serialization,我正在尝试序列化一些表单数据,以便可以将其填充到一个隐藏字段中,直到用户准备提交整个表单为止(想象一下向导) 我正在尝试这个: print simplejson.dumps(vehicle_form.cleaned_data) json = json_encode(vehicle_form.cleaned_data) data = json_decode(json) vehicle = Vehicle(**data) 但我经常会遇到这样的错误: <VehicleMake: Honda&

我正在尝试序列化一些表单数据,以便可以将其填充到一个隐藏字段中,直到用户准备提交整个表单为止(想象一下向导)

我正在尝试这个:

print simplejson.dumps(vehicle_form.cleaned_data)
json = json_encode(vehicle_form.cleaned_data)
data = json_decode(json)
vehicle = Vehicle(**data)
但我经常会遇到这样的错误:

<VehicleMake: Honda> is not JSON serializable
给出:

'str' object has no attribute '_meta'
大概是因为它正在迭代键,这些键都是字符串,而我认为它需要一个queryset,而我没有

那我该怎么做呢


好的,到目前为止我已经想到了这个:

from django.utils.simplejson import JSONEncoder, dumps, loads
from django.utils.functional import curry
from django.db.models import Model
from django.db.models.query import QuerySet
from django.core.serializers import serialize

class DjangoJSONEncoder(JSONEncoder):
    def default(self, obj):
        if isinstance(obj, Model):
            return obj.pk
        elif isinstance(obj, QuerySet):
            return loads(serialize('json', obj, ensure_ascii=False))
        return JSONEncoder.default(self, obj)

json_encode = curry(dumps, cls=DjangoJSONEncoder)
json_decode = loads
根据我在[这里][1]找到的答案。现在我试着这样做:

print simplejson.dumps(vehicle_form.cleaned_data)
json = json_encode(vehicle_form.cleaned_data)
data = json_decode(json)
vehicle = Vehicle(**data)
前两行工作正常,但第三行导致异常:

Cannot assign "3": "Vehicle.model" must be a "VehicleModel" instance.

接近!虽然不知道如何处理这个问题…

这有点像黑客,但我不知道有什么更好的方法:

try:
    vehicle_data = simplejson.loads(request.POST['vehicle_data'])
except ValueError:
    vehicle_data = []
vehicle_data.append(vehicle_form.raw_data())
request.POST['vehicle_data'] = simplejson.dumps(vehicle_data)
它从表单中的隐藏字段获取JSON数据,并将其解码为Python dict。如果它不存在,它将启动一个新列表。然后,它附加新的原始/未清理数据并对其重新编码,并将其转储到隐藏字段中

要使其正常工作,您需要复制POST数据(
request.POST.copy()
),使其变为可变的,或者像我那样对其进行破解:
request.POST.\u mutable=True

在我的表单模板中,我放置了以下内容:

<input type="hidden" name="vehicle_data" value="{{request.POST.vehicle_data}}" />

因为
.data
返回的数据太多(事实上,它只是返回您最初传入的POST数据),加上它有前缀,这是我不想要的。

这有点像黑客,但我不知道更好的方法:

try:
    vehicle_data = simplejson.loads(request.POST['vehicle_data'])
except ValueError:
    vehicle_data = []
vehicle_data.append(vehicle_form.raw_data())
request.POST['vehicle_data'] = simplejson.dumps(vehicle_data)
它从表单中的隐藏字段获取JSON数据,并将其解码为Python dict。如果它不存在,它将启动一个新列表。然后,它附加新的原始/未清理数据并对其重新编码,并将其转储到隐藏字段中

要使其正常工作,您需要复制POST数据(
request.POST.copy()
),使其变为可变的,或者像我那样对其进行破解:
request.POST.\u mutable=True

在我的表单模板中,我放置了以下内容:

<input type="hidden" name="vehicle_data" value="{{request.POST.vehicle_data}}" />

由于
.data
返回的数据太多(事实上,它只返回您最初传入的POST数据),加上前缀,这是我不想要的。

哇,这是相当多的黑客=)您检查过django formwizard()了吗?它基本上允许您指定表单序列,并处理步骤之间的数据存储。如果你有多个模型实例,你也可以在那里有一个模型表单,或者一个表单集。@Anton:嗯。。。这不是一个真正的巫师,这只是最简单的解释方法。实际上,它是一个带有子窗体的窗体,您可以在其中添加任意数量的项。当您单击“添加”时,它会将所有数据发布回同一页面,将子表单数据序列化到一个隐藏字段中,并将其清除,以便您可以添加另一个字段。因此,您有一个无JS的“动态”表单,您可以在其中添加任意数量的项。我觉得很酷,而且也没那么黑。。。它实际上是一个非常干净的解决方案,与我以前尝试的解决方案相反。@Anton:那页上的“内容”列表。。。我花了一段时间才意识到这些都是链接。与普通文本颜色相同,在悬停之前没有下划线..hrm。。还有,这一款比django附带的一款有什么优势?嗯,
django formwizard
实际上将成为
contrib.formtools.wizard
,因此,如果您使用的是最新的django开发版本,那么我想您已经可以使用它了。但是如果你坚持使用Django的稳定版本,请使用
Django formwizard
app(旧的contrib formwizard不好)。@Anton:噢。很公平。是的,我现在正在运行稳定的1.3。哇,这是相当多的黑客=)你检查过django formwizard()了吗?它基本上允许您指定表单序列,并处理步骤之间的数据存储。如果你有多个模型实例,你也可以在那里有一个模型表单,或者一个表单集。@Anton:嗯。。。这不是一个真正的巫师,这只是最简单的解释方法。实际上,它是一个带有子窗体的窗体,您可以在其中添加任意数量的项。当您单击“添加”时,它会将所有数据发布回同一页面,将子表单数据序列化到一个隐藏字段中,并将其清除,以便您可以添加另一个字段。因此,您有一个无JS的“动态”表单,您可以在其中添加任意数量的项。我觉得很酷,而且也没那么黑。。。它实际上是一个非常干净的解决方案,与我以前尝试的解决方案相反。@Anton:那页上的“内容”列表。。。我花了一段时间才意识到这些都是链接。与普通文本颜色相同,在悬停之前没有下划线..hrm。。还有,这一款比django附带的一款有什么优势?嗯,
django formwizard
实际上将成为
contrib.formtools.wizard
,因此,如果您使用的是最新的django开发版本,那么我想您已经可以使用它了。但是如果你坚持使用Django的稳定版本,请使用
Django formwizard
app(旧的contrib formwizard不好)。@Anton:噢。很公平。是的,我现在跑的是稳定的1.3。