django - 无法分配外键

jli*_*eza 2 python mysql sqlite django

由于未知原因,我无法将Item_rarity表的外键实例分配到Detailed_item表中.Django抛出一个错误:

无法分配"u'Basic":"Detailed_item.rarity"必须是"Item_rarity"实例.

...但是在Item_rarity字典中存在"基本"记录 - 我可以从管理面板中选择它并Detailed_item手动创建记录.

我已经定义了模型:

class Detailed_item(models.Model):
    item_id = models.IntegerField(primary_key=True)
    name = models.CharField(max_length=50)
    level = models.IntegerField()
    icon = models.CharField(max_length=150)
    rarity = models.ForeignKey('Item_rarity')
    general_type = models.ForeignKey('Item_type')
    detailed_type = models.ForeignKey('Item_detailed_type')

class Item_rarity(models.Model):
    name = models.CharField(max_length=15, primary_key=True)

class Item_type(models.Model):
    name = models.CharField(max_length=15, primary_key=True)

class Item_detailed_type(models.Model):
    name = models.CharField(max_length=20, primary_key=True)
Run Code Online (Sandbox Code Playgroud)

在视图中,我尝试以这种方式填充它(插入多个项目):

...
   items = get_all_items()  #get dict of items
        for element in items:
            tmp_det_type = ''
            for key, val in element.iteritems():
            #get 'detailed type' from inner dict
                if key == "type":
                    tmp_det_type = val

            item = Detailed_item(
                item_id=element['id'],
                name=element['name'],
                level=element['level'],
                icon=element['icon'],
                rarity=element['rarity'],  #error
                general_type=element['type'],
                detailed_type=tmp_det_type,
                )

            item.save()

...
Run Code Online (Sandbox Code Playgroud)

我甚至试图硬编码"Basic"字符串,但它也不起作用.

*解决* 下面的两个条目,这是Item_typeItem_detailed_type也无效.正确的代码:

from app.models import Detailed_item, Item_rarity, Item_type, Item_detailed_type
...
   items = get_all_items()  #get dict of items
        for element in items:
            tmp_det_type = ''
            for key, val in element.iteritems():
            #get 'detailed type' from inner dict
                if key == "type":
                    tmp_det_type = val

                #create objects with string values
                obj_rarity = Item_rarity(name=element['rarity'])
                obj_item_type = Item_type(name=element['type'])
                obj_item_detailed_type = Item_detailed_type(name=tmp_det_type)

                item = Detailed_item(
                    item_id=element['id'],
                    name=element['name'],
                    level=element['level'],
                    icon=element['icon'],
                    rarity=obj_rarity,
                    general_type=obj_item_type,
                    detailed_type=obj_item_detailed_type,
                    )


            item.save()

...
Run Code Online (Sandbox Code Playgroud)

Jag*_*u T 9

Item_rarityDetailed_item因为Item_rarity是Detailed_item中的外键相关对象,所以应该在存储对象时传递实例.

它可能你已经传递了Basic字符串而不是<Basic Object>它自己.

在使用ORM在django中创建对象时,任何与foreign_key相关的对象都应该提供实例本身而不是对象的id(pk),而从数据库中获取数据时,您可以使用实例或id (pk)实例.

class ParentModel(models.Model):
    model_field = models.CharField(max_length=16)

class MyModel(models.Model):
    some_field = models.ForeignKey('ParentModel')

parent_model = ParentModel.objects.create(model_field='some_data')

my_model = MyModel.objects.create(some_field=parent_model)
                                             ^^^^^^^^^^^^
Run Code Online (Sandbox Code Playgroud)

请注意,传递parent_model对象本身而不是id

在取回数据的同时,

parent_model = ParentModel.objects.get(model_field='some_data')

my_model = MyModel.objects.get(some_field=parent_model)

or

my_model = MyModel.objects.get(some_field=parent_model.id)
Run Code Online (Sandbox Code Playgroud)

两者都适用于数据提取.