上一个笔记写了如何添加一个应用,现在来说明如何给这个应用添加一个后台管理模块。
首先需要在应用的根目录底下新建一个admin.py的类。
#! /usr/bin/python
# -*- coding:utf-8 -*-
'''
Created on 2011-3-12
@author: ezioruan
'''
from django.contrib import admin
from DjangoTest.orders.models import Order,OrderDetail
class OrderDetailLine(admin.StackedInline):
model = OrderDetail
class OrderDetailLine2(admin.TabularInline):
model = OrderDetail
class OrderAdmin(admin.ModelAdmin):
# fields = ['order_date', 'order_creater']
fieldsets = [
('order date',{'fields':['order_date']}),
('created by ',{'fields':['order_creater'],'classes':['collapse']}),
# 因为 is_order_today 是通过property方法进行赋值的,所有没有办法在django里面加载
# ('is ordey today ',{'fields':['is_order_today']}),
]
list_display = ['order_creater','is_order_today']
list_filter = ['order_date']
inlines = [OrderDetailLine,OrderDetailLine2]
# readonly_fields = ['order_creater']
admin.site.register(Order, OrderAdmin);
这样在后台的时候,会在界面中载入这个类的管理,
admin.site.register(Order, OrderAdmin);
将一个类添加到后台管理,这样就可以使用默认的管理员模板来进行管理了。
这个方法的参数,第一个是要进行管理的类,第2个是管理类。
如果只是第一个参数,那么就会使用默认的模板进行管理,
第2个参数是自己实现的类,可以进行定制管理。
# fields = ['order_date', 'order_creater']
fields属性定义要进行管理的字段,
也可以用fieldset进行管理,就是针对每个字段进行定制
fieldsets = [
('order date',{'fields':['order_date']}),
('created by ',{'fields':['order_creater'],'classes':['collapse']}),
# 因为 is_order_today 是通过property方法进行赋值的,所有没有办法在django里面加载
# ('is ordey today ',{'fields':['is_order_today']}),
]
这边的第一个参数是tab页的标题,还可以设置class属性,
然后我查看源码的时候发现了一个函数,发现它的fieldset是通过一个property函数进行设置的
def _declared_fieldsets(self):
if self.fieldsets:
return self.fieldsets
elif self.fields:
return [(None, {'fields': self.fields})]
return None
declared_fieldsets = property(_declared_fieldsets)
仔细查了一下这个的用法,发现property就是进行一系列get set del方法的设置
2.1 Built-in Functions
property( [fget[, fset[, fdel[, doc]]]])
Return a property attribute for new-style classes (classes that derive from object).
fget is a function for getting an attribute value, likewise fset is a function for setting, and fdel a function for del'ing, an attribute. Typical use is to define a managed attribute x:
If given, doc will be the docstring of the property attribute. Otherwise, the property will copy fget's docstring (if it exists). This makes it possible to create read-only properties easily using property() as a decorator:
大概含义是,如果要使用property函数,首先定义class的时候必须是object的子类。通过property的定义,当获取成员x的值时,就会调用getx函数,当给成员x赋值时,就会调用setx函数,当删除x时,就会调用delx函数。使用属性的好处就是因为在调用函数,可以做一些检查。如果没有严格的要求,直接使用实例属性可能更方便。
所以我就做了个实验,在我的类中加了一个属性和方法,但是发现这样子做以后不能在django的后台进行管理了,会提示没有这个属性,
def _is_order_today(self): return self.order_date.date() == datetime.date.today() def set_order_date(self,order_date): self.order_date = order_date is_order_today = property(_is_order_today,set_order_date)
进行debug,发现是每个属性都要是models里面的属性才可以,这样才能和数据库映射起来
主从表的管理,可以在这边设置inlines属性,加入子表的管理模式。
这边用了2种不同的风格进行管理,但是发现保存的时候,要是2种同时修改的话,只会保存后面的一个。