【问题标题】:Custom column names on Django ManyToMany fieldsDjango ManyToMany 字段上的自定义列名
【发布时间】:2013-08-04 06:40:10
【问题描述】:

我正在为 django 中的 java 应用程序构建 UI。我想根据 JPA 创建的表创建 Java 表。为此,当我使用 ManyToMany 字段时,新创建的中间表的列名与 JPA 的列名不匹配。

有什么方法可以为表中的列提供自定义名称所以,以免在 Java 中出现 Missing column 错误。

任何帮助将不胜感激。

【问题讨论】:

    标签: django model django-admin customization django-orm


    【解决方案1】:

    我认为您可以使用db_column 参数来完成此操作。

    这看起来像:my_m2m_field=models.ManytoManyField(Model, db_name="Desired Name")

    【讨论】:

    • 我也尝试过使用它和 db_column,但它绝不会更改列名。
    • @Akshay 是否删除了生成的表并再次运行syncdb? Django 不能自己改变现有的表。
    • 是的,我总是在对测试代码进行一些更改后删除现有表。到目前为止,尝试了很多不同的方法,但没有成功。我觉得它必须是非常微不足道的事情。
    • 我认为您混淆了 db_columndb_name 参数。如果不使用直通表,似乎不可能更改 many_to_many 关系的列名。在那里你确实可以使用 db_column 参数,但使用 db_name 参数对列名没有影响
    【解决方案2】:

    您可以指定自定义through 模型,而无需指定任何额外字段。然后您可以在ForeignKey 字段中使用db_column=...

    class A(models.Model):
        ...
    
    class B(models.Model):
        a = models.ManyToManyField(A, through='C', db_table='customtablename')
    
    class C(models.Model):
        a = models.ForeignKey(A, db_column='customcolumnname')
        b = models.ForeignKey(B, db_column='secondcustomcolumnname')
    

    【讨论】:

    • 谢谢。但我确实为显示添加了一些我认为在使用“通过”时必不可少的东西
    • 有没有办法做到这一点而不必创建“通过”模型?我试图在 ManyToMany 中间表中有一个自定义外键列。有没有办法让 ManyToManyField 将 db_column 作为参数?
    • @klandshome 总有办法。有什么好办法吗?当然不。您可以在模型定义之后(例如class_prepared 信号)直接在<Model>.<m2m_field>.through.<fk_field> 上设置db_column,但不能保证某些其他代码在更改之前不会使用模型。跨度>
    • toppings = models.ManyToManyField(Topping, db_table='pizza_link_topping') 这个例子好吗?我的意思是它可以工作并且确实允许中间表具有自定义名称 Pizza_link_table。只是无法让它与自定义外键列一起使用..
    • 也就是说through是最“优雅”的方式?仅仅为了获取自定义外键列是否值得使用它?
    【解决方案3】:

    正如上面提到的knbk,它确实是出路,下面是我完成它的完整方法。

    class A(models.Model):
    ....
    
    class B(models.Model):
        a = models.ManyToManyField(A,through = 'C', db_table = 'customtablename')
    
    class C(models.Model):
        a = models.ForeignKey(A,db_column='customcolumnname')
        b = models.ForeignKey(B,db_column='secondcustomcolumnname')
    

    在管理控制台上显示它之后,您必须使用内联,以便可以同时更改两个模型。(我认为这又是一个选择/要求的问题)。这样做的方法是,

    在 admin.py 中

    class ABInline(admin.TabularInline):
        model = B.a.through
    
    class AAdmin(admin.ModelAdmin):
        inlines = [ABInline,]
    
    class BAdmin(admin.ModelAdmin):
        inlines = [ABInline,]
        exclude = ('a',)
    

    admin.register.site(B,BAdmin)

    这个模型可以注册到你想要的任何模型中。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-01-15
      • 1970-01-01
      • 1970-01-01
      • 2014-05-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多