2011-08-20 73 views
3

對於外鍵的多列唯一約束,MySQL似乎有些破裂。這是我能拿出來顯示這個(使用MySQL/InnoDB的)最小的例子:我如何在MySQL中有一個涉及ForeignKey字段的unique_together約束?

models.py

from django.db import models 

class Team(models.Model): 
    pass 

class Player(models.Model): 
    team = models.ForeignKey(Team) 
    number = models.PositiveIntegerField() 

    class Meta: 
     unique_together = ("team", "number") 

運行schemamigration --initial,南吐出來,下面的遷移(唯一重要的位):

class Migration(SchemaMigration):                                     
    def forwards(self, orm): 
     # Adding model 'Team' 
     db.create_table('fkuniq_team', (
      ('id', self.gf('django.db.models.fields.AutoField')(primary_key=True)), 
     )) 
     db.send_create_signal('fkuniq', ['Team']) 

     # Adding model 'Player' 
     db.create_table('fkuniq_player', (
      ('id', self.gf('django.db.models.fields.AutoField')(primary_key=True)), 
      ('team', self.gf('django.db.models.fields.related.ForeignKey')(to=orm['fkuniq.Team'])), 
      ('number', self.gf('django.db.models.fields.PositiveIntegerField')()), 
     )) 
     db.send_create_signal('fkuniq', ['Player']) 

     # Adding unique constraint on 'Player', fields ['team', 'number'] 
     db.create_unique('fkuniq_player', ['team_id', 'number']) 

而且在MySQL:

mysql> SHOW COLUMNS FROM fkuniq_player; 
+---------+------------------+------+-----+---------+----------------+ 
| Field | Type    | Null | Key | Default | Extra   | 
+---------+------------------+------+-----+---------+----------------+ 
| id  | int(11)   | NO | PRI | NULL | auto_increment | 
| team_id | int(11)   | NO | MUL | NULL |    | 
| number | int(10) unsigned | NO |  | NULL |    | 
+---------+------------------+------+-----+---------+----------------+ 

我想靜靜地南未能創造出我想要的獨特約束。在Key專欄中,我看到id主鍵索引和team_id外鍵索引,但也應該有一個MULnumber行,因爲應該就可以了UNIQUE指數與team_id。此外,從模型中移除unique_together約束會導致下遷移失敗,出現錯誤:

Traceback (most recent call last): 
    ... 
    File "/home/aogier/uniques/../uniques/fkuniq/migrations/0002_auto__del_unique_player_number_team.py", line 12, in forwards 
    db.delete_unique('fkuniq_player', ['number', 'team_id']) 
    File "/home/aogier/.virtualenvs/uniques/lib/python2.7/site-packages/south/db/generic.py", line 479, in delete_unique 
    raise ValueError("Cannot find a UNIQUE constraint on table %s, columns %r" % (table_name, columns)) 
ValueError: Cannot find a UNIQUE constraint on table fkuniq_player, columns ['number', 'team_id'] 

我相信這是因爲缺少MySQL沒有發揮好,當外鍵約束和多列UNIQUE約束一致。對於ALTER TABLEhttp://dev.mysql.com/doc/refman/5.1/en/alter-table.html的MySQL文檔有一個評論意見(參見下文,Hadi Rastgou評論)。

不管怎樣,對於長期問題抱歉:沒有人有辦法讓這項工作?即使我必須在原始SQL中的特定於MySQL的查詢中編寫代碼,我也會喜歡在遷移中執行此操作的乾淨方式。或者,也許這在MySQL中是不可能做到的,在我花更多時間研究這個之前,這很好理解。

回答

相關問題