2015-11-03 97 views
0

是否可以構建一個自定義模型字段/窗口小部件組合,該組合顯示值但不會將任何內容寫回數據庫?我只會在管理員的表單中使用這個小部件。創建僅顯示(不可編輯)的Django管理員字段

我寫了自己的字段,它覆蓋了formfield()方法來聲明它自己的窗口小部件類。它顯示就好了,但只要「保存」按鈕被點擊的管理員,我得到驗證錯誤:

This field is required. 

這是有道理的,考慮到我的窗口小部件沒有呈現出一種形式領域。但是,我想要做的是基本上從更新過程中刪除該字段:無論何時在管理中使用,它都不應該在SQL UPDATE中提及。

這可能嗎?

下面的代碼的素描時,我到目前爲止有:

class MyWidget(Widget): 
    def render(self, name, value, attrs=None): 
     if value is None: 
      value = "" 
     else: 
      # pretty print the contents of value here 
      return '<table>' + ''.join(rows) + '</table>' 

class MyField(JSONField): 
    def __init__(self, *args, **kwargs): 
     kwargs['null'] = False 
     kwargs['default'] = list 
     super(MyField, self).__init__(*args, **kwargs) 

    def formfield(self, **kwargs): 
     defaults = { 
      'form_class': JSONFormField, 
      'widget': MyWidget, 
     } 
     defaults.update(**kwargs) 
     return super(MyField, self).formfield(**defaults) 

更新1:用例是外地代表的審計日誌。在內部,它會定期寫入。然而,管理員永遠不需要寫入它,它只需要以非常可讀的格式呈現出來。

我沒有在應用程序中使用任何其他的ModelForms,所以管理員是唯一的窗體用戶。我不想在管理類本身上實現這種行爲,因爲這個字段將在各種模型中重用,並且總是應該以相同的方式運行。

+0

作爲一種臨時解決方案,我已經爲我的窗口小部件渲染器添加了一個隱藏字段,但這只是感覺不對:現在我通過瀏覽器發送序列化的字段內容,然後將它們反序列化,而不僅僅是從保存操作中刪除這一個字段。 –

回答

1

我可能對你想要的有點困惑,但你可能想看看模型屬性。這是我目前的項目的一個例子。

代碼模型裏面:

class Textbook(models.Model): 
    #other fields 

    @property 
    def NumWishes(self): 
     return self.wishlist_set.count() 

然後,你可以將其顯示在管理頁面上。

class Textbook_table(admin.ModelAdmin): 
    fields = ["""attributes that are saved in the model"""] 
    list_display = ("""attributes that are saved in the model""", 'NumWishes'') 

因此,現在我可以在管理頁面中顯示NumWishes,但不需要使用該模型創建NumWishes。

+0

那麼,我需要它來支持一個字段,因爲它是存儲在數據庫中的實際數據,並且會被我的應用程序修改。我只想在管理員中以一種額外的可讀格式呈現它,並且我從不想在管理員中對其進行編輯。 –

+0

嗯,我從來沒有這樣做過。抱歉! – Programmingjoe

5

有多種方法可以在管理頁面中創建只讀字段。您對數據庫存儲的要求有點模糊,所以我會通過選項。

你必須在admin.py先註冊一個AdminModel:

from django.contrib import admin 
from yourapp.models import YourModel 

class YourAdmin(admin.ModelAdmin): 
    pass 

admin.site.register(YourModel, YourAdmin) 

現在你可以在不同的行爲,將其添加。例如,您可以添加在編輯顯示的字段列表/添加頁面:

class YourAdmin(admin.ModelAdmin): 
    fields = ['field1', 'field2'] 

這可能是示範田,示範性或模型方法的名稱。方法顯示爲只讀。

如果你想有一個字段只讀明確補充一點:

​​

然後,你必須完全通過添加一個方法具有相同名稱覆蓋字段的顯示選項。你甚至不會需要一個模型字段/方法使用該名稱,則:

class YourAdmin(admin.ModelAdmin): 
    fields = ['field1', 'field2'] 
    readonly_fields = ['field2'] 

    def field2(self, obj): 
     return '*** CLASSIFIED *** {}'.format(obj.field2) 

隨着django.utils.safestring.mark_safe可以返回HTML代碼。

管理員的所有其他選項都可用,但小部件配置除外,因爲它僅適用於可寫字段。

+0

感謝您的詳細的概述,很好的總結不同的選項!然而,我希望將這種行爲與字段類型本身相關聯,因爲我打算在各種模型中重用它,它將僅由應用程序(它基本上是一個審計日誌)寫入,但始終是隻讀的管理員。 –

+0

這實際上是管理模型配置從數據模型移動到管理模型的原因。但是,您可以通過檢查字段的類型來對任何模型字段進行子類化,並從模型中動態生成'readonly_fields'。 –

相關問題