问题描述
我使用django作为后端,并且运行良好,但是在尝试替换 text = models.TextField(blank=True,null=True)
text = models.JSONField(blank=True,null=True)
之后,我得到了
文本字段显示为带斜杠\
"text": "{\"name\": [\"test\",\"test2\"]}",
而样式字段看起来像json
"style": {
"borderRadius": "5px","backgroundColor": "orange"
},
尽管它们都是jsonfield。
models.py
class elements(models.Model):
tag = models.CharField(blank=True,null=True,max_length=20)
# it was # text = models.TextField(blank=True,null=True)
# Now it is
text = models.JSONField(blank=True,null=True)
src = models.TextField(blank=True,null=True)
style = models.JSONField(blank=True,null=True)
main = models.ForeignKey(
'self',blank=True,related_name="sub",on_delete=models.PROTECT)
def __str__(self):
return "<elements: {} {}>".format(self.tag,self.text,self.src,self.style)
def __repr__(self):
return self.__str__()
在运行python manage.py makemigrations
然后python manage.py migrate
之后,我也遇到了错误
DETAIL: Token "add" is invalid.
CONTEXT: JSON data,line 1: add...
the full error
Operations to perform:
Apply all migrations: account,admin,auth,authtoken,contenttypes,myapp,sessions,sites
Running migrations:
Applying myapp.0006_auto_20200905_1410...Traceback (most recent call last):
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/utils.py",line 84,in _execute
return self.cursor.execute(sql,params)
psycopg2.errors.InvalidTextRepresentation: invalid input Syntax for type json
DETAIL: Token "add" is invalid.
CONTEXT: JSON data,line 1: add...
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "manage.py",line 22,in <module>
main()
File "manage.py",line 18,in main
execute_from_command_line(sys.argv)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/__init__.py",line 401,in execute_from_command_line
utility.execute()
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/__init__.py",line 395,in execute
self.fetch_command(subcommand).run_from_argv(self.argv)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/base.py",line 330,in run_from_argv
self.execute(*args,**cmd_options)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/base.py",line 371,in execute
output = self.handle(*args,**options)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/base.py",line 85,in wrapped
res = handle_func(*args,**kwargs)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/core/management/commands/migrate.py",line 245,in handle
fake_initial=fake_initial,File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/migrations/executor.py",line 117,in migrate
state = self._migrate_all_forwards(state,plan,full_plan,fake=fake,fake_initial=fake_initial)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/migrations/executor.py",line 147,in _migrate_all_forwards
state = self.apply_migration(state,migration,line 227,in apply_migration
state = migration.apply(state,schema_editor)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/migrations/migration.py",line 124,in apply
operation.database_forwards(self.app_label,schema_editor,old_state,project_state)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/migrations/operations/fields.py",line 236,in database_forwards
schema_editor.alter_field(from_model,from_field,to_field)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/base/schema.py",line 572,in alter_field
old_db_params,new_db_params,strict)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/postgresql/schema.py",line 168,in _alter_field
new_db_params,strict,File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/base/schema.py",line 726,in _alter_field
params,line 142,in execute
cursor.execute(sql,params)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/utils.py",line 98,in execute
return super().execute(sql,line 66,in execute
return self._execute_with_wrappers(sql,params,many=False,executor=self._execute)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/utils.py",line 75,in _execute_with_wrappers
return executor(sql,many,context)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/utils.py",params)
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/utils.py",line 90,in __exit__
raise dj_exc_value.with_traceback(traceback) from exc_value
File "/Users/apple/Desktop/learning web stack from clonning notion.so/backend/env/lib/python3.7/site-packages/django/db/backends/utils.py",params)
django.db.utils.DataError: invalid input Syntax for type json
DETAIL: Token "add" is invalid.
CONTEXT: JSON data,line 1: add...
解决方法
为了将Text-Field转换为JSON-Field,您可以使用类似于以下内容的4步策略:
- 在模型中创建一个新的JSON列
- 使用
--empty
添加新的迁移,并使用RunPython运行python函数,以选择整个模型,加载旧的旧值,然后使用json.loads
将其转换为JSON对象并保存在新列中 - 删除旧的“文本字段”列
- 将较新的列重命名为原始列名