2013-05-31 47 views
1

我有一個CharField的典範作用或多或少的枚舉遷移CharField枚舉SmallIntegerField:Django的:利用南

grade = models.CharField(max_length='1', choices=('A', 'B', 'C'))

不幸的是,有些複雜的原因,我必須遷移它是一個SmallIntegerField,像這樣:

grade = models.SmallIntegerField(choices=(1, 2, 3))

我將如何做到這一點在南非?我有幾個一般的想法,但我不確定如何執行它們。我首先想到的是一系列的遷移:

  1. 到新的等級增加一個新的grade_new SmallIntegerField和翻譯老牌號它(移民的前進方法的過程中)。
  2. 刪除舊grade領域,同時更名grade_newgrade

這是正確的做法?如果是這樣的話,我會如何在第一步中將舊成績轉化爲新成績?

回答

2

儘管我仍然很想知道這種方法是否正確,但我只能通過兩次遷移/提交來了解如何執行上述計劃。

class Foo(models.Model): 
    A, B, C = 'A', 'B', 'C' 
    A2, B2, C2, = 1, 2, 3 
    grade = models.CharField(max_length='1', choices=((A, 'A'), (B, 'B'), (C, 'C'))) 
    new_grade = models.SmallIntegerField(choices=((A2, 1), (B2, 2), (C2, 3))) 

    class Meta: 
    ordering = ['x', 'new_grade'] 
    unique_together = ('x', 'new_grade') 

後:

首先,我在模型的Meta類的orderingunique_together字段中添加一個new_grade = models.SmallIntegerField(choices=(1, 2, 3))場模型(這需要複製枚舉瓦爾),並更新了引用gradenew_grade運行manage.py schemamigration app --auto,我打開遷移文件並將正向方法修改爲:

def forwards(self, orm): 
    # For the unique_together... 
    db.delete_unique('app_foo', ['x', 'grade']) 

    db.add_column('app_foo', 'new_grade', 
       self.gf('django.db.models.fields.SmallIntegerField')(default=1), 
       keep_default=False) 
    if not db.dry_run: 
    mapping = {'A': 1, 'B': 2, 'C': 3} 
    for foo in orm.Foo.objects.all(): 
     foo.new_grade = mapping[foo.grade] 
     foo.save() 

    # For the unique_together... 
    db.create_unique('app_foo', ['x', 'new_grade']) 

運行後manage.py migrate app,所有Foos現在都有一個帶有映射值的重複new_grade字段。在那時我承諾我的代碼,因爲它處於穩定狀態。

其次,在models.py,我刪除了舊grade場,改名爲重複枚舉增值經銷商,又在Meta類的引用更新爲new_grade

class Foo(models.Model): 
    A, B, C, = 1, 2, 3 
    grade = models.SmallIntegerField(choices=((A, 1), (B, 2), (C, 3))) 

    class Meta: 
    ordering = ['x', 'grade'] 
    unique_together = ('x', 'grade') 

我再次跑到manage.py schemamigration app --auto並打開遷移文件修改前的方法:

def forwards(self, orm): 
    # For the unique_together... 
    db.delete_unique('app_foo', ['x', 'new_grade']) 

    db.delete_column('app_foo', 'grade') 
    db.rename_column('app_foo', 'new_grade', 'grade') 

    # For the unique_together... 
    db.create_unique('app_foo', ['x', 'grade']) 

運行manage.py migrate app後,所有的FOOS現在有自己的grade領域取代與前者new_grade字段和遷移完成!