2016-06-09 105 views
1

我有一個設置,我有幾個模型其中兩個是OptionProjectOptions代表我的應用程序中幾個字段的選擇選項,並存儲大約1000(默認)值。我現在想要達到的是Projects可以有自己的一套Options,這意味着當他們開始一個新的Project時,他們將看到默認的選項集。然而他們可以刪除一些選項,然後將不會顯示在他們的項目(但留在數據庫中)以及添加自定義選項到他們的項目(其他人不應該能夠看到)。常見用例是用戶可能希望保留默認Options的99%,以便它們將刪除10並可能添加10.Django模型多對多替代

如何爲描述的案例建模?我是否需要創建一個ManyToMany字段Project <-> Option,我將在創建項目時填充所有Options,或者是否有更好,更省空間的方式可供您考慮,例如:以某種方式存儲刪除的ID在某處,並找到一種方法來顯示默認Options +項目特定Options

我的模型,像這樣:

class Option(models.Model): 
    creator = models.ForeignKey(settings.AUTH_USER_MODEL, related_name="selectoptions", blank=True, null=True) 
    created = models.DateField(auto_now_add=True) 
    deleted = models.BooleanField(default=False) 

    name = models.CharField(max_length=255) 

    #we can have nested selectoptions 
    parent = models.ForeignKey('self', blank=True, null=True, related_name='children', db_index=True) 

class Project(models.Model): 
    name = models.CharField(max_length=200) 
    users = models.ManyToManyField(settings.AUTH_USER_MODEL, related_name='projects') 

回答

2

你可以有你的項目模型,例如

class Project(models.Model): 
    name = models.CharField(max_length=200) 
    options = models.ManyToManyField(Option, blank=True) 
    anyother field you wish to have 

,您可以與您可以選擇的模式,應該足夠了繼續。

現在讓我們說你有選擇1,2,3,4,5和項目A和B

一個可以有選擇1,2,3和可以有選擇2,3, 4,5。

而且,你不希望有選擇1項目一個,你只需從M2M領域被這句話

projectA.options.remove(option1) 

所以,你已經刪除選項1,從項目中刪除它,但它仍然存在在數據庫中,你可以通過使用聲明

projectB.options.add(option1) 

所以,現在當你做同樣的選項1添加到項目B

projectA.options.all() 

你的輸出就會選項2,選項3

projectB.options.all()會給選項1,選項2,選項3,選項4,選項5。

我希望我已經正確解釋過,如果不清楚的話留下評論,會很樂意提供幫助。

編輯:是的,這是它應該如何應對您的情況,除非您獲得替代方式。

編輯2

發佈問題更新,你可以刪除的選項,從項目M2M領域,並有通過名稱ProjectOption一個單獨的模型。它可能就像,

class ProjectOption(models.Model): 
    project = models.ForeignKey(Project) 
    option = models.ForeignKey(Option) 
    is_deleted = models.BooleanField(default=False) 

你仍然需要填充它,它是一次性操作。所以現在,每個項目都會有你的默認選項,如果用戶選擇刪除一個,你可以設置is_deleted = True或實際刪除它。這將爲您提供刪除選項的詳細信息(僅當您不實際刪除對象時,只需設置is_deleted = True)。

+0

問題是,當我創建一個新的項目時,我總是要做:'selectOptions = Option.objects.all()newProject.options.add(* selectOptions)'這將是一個巨大的開銷,因爲它會爲所有項目創建數據庫條目。我希望以某種方式存儲已刪除的selectoptions的ID,並且可能只接收來自默認項目的selectOptions +當前項目的selectOptions – niklas

+0

我可以知道這是一個問題嗎?以及爲什麼你必須做newProject.options.add(* selectOptions)。看,選項是獨立的實體。當你創建一個newProject時,它不會有任何選項嗎?所以,它的M2M選項領域不會有任何東西。只有當用戶選擇添加該選項時才填充它。 –

+0

當你做newProject.options.add(* selectOptions)時,你不必要地用選項填充newProject,然後讓用戶刪除不需要的,當它應該像讓用戶添加/刪除任何他想要的。 –