Sadmin封装了两个基础类,分别是ListCreateView
和RetrieveUpdateDestroyView
,用来快捷的实现model的增删改查功能
ListCreateView用来实现model(表)级别的操作,包括列出表里的数据,以及往表里插入数据,分别对应了get
和post
两个方法,用法如下:
from sadmin.commons.options import ListCreateView, RetrieveUpdateDestroyView
class TaskList(ListCreateView):
model = Task
template = 'engine/task.index.html'
permission = {'get': 'engine.task_select', 'post': 'engine.task_change'}
接收两个方法,分别是get
和post
get: 获取数据列表
post: 添加单条数据
接收几个变量,分别是:model
、filter
、orderby
、list_display
、search_fields
、project_filter
、queryset_limit
、template
、permission
model: 要操作的model
filter: 字符串,在默认QuerySet结尾增加filter,默认QuerySet是self.model.objects.all()
或self.model.objects.filter(is_deleted=False)
,根据model中是否有is_deleted
字段来确定,当filter有值时,则会在QuerySet后跟上filter的值,例如filter='.filter(state=8)'
,则最终的QuerySet语句就是self.model.objects.all().filter(state=8)
orderby: 列表,根据orderby定义的排序列表,生成排序语句添加到QuerySet结尾,例如orderby=['-id']
,则最终的QuerySet语句是self.model.objects.all().order_by("-id")
,orderby位于QuerySet的末尾
list_display: 列表,定义要显示的字段,默认显示所有字段,如果list_display
存在时则显示list_display
定义的字段,主要在最终返回时过滤,通过model_to_dict
的fields
实现model_to_dict(_data, fields=self.list_display, exclude=self.many_to_many_fields)
,所以当list_display
与model定义的to_dict
冲突时,以to_dict
为准
search_fields: 列表,定义模糊搜索时搜索的字段,默认会搜索所有['GenericIPAddressField', 'CharField', 'TextField', 'EmailField', 'JSONField']类型的字段,若search_fields
存在,则会在search_fields
定义的字段中搜索
project_filter: 布尔值,定义是否根据project过滤,默认为True,当表字段中存在project字段时,仅过滤用户当前project的数据,用户当前project从两个地方获取,1.用户请求里的project参数,2.浏览器Cookies里的project参数
queryset_limit: 布尔值,定义是否限制数据展示条数,默认为True,也就是默认限制数据展示条数,默认最多展示100条数据,当需要一次性展示所有数据时,可以设置为False,注意:当表数据较多时设置为False会有性能问题
template: 字符串,定义list模板,如果模板为空则返回JsonResponse,如果模板不为空则返回render并附带lPage
变量,可直接在模板中循环使用
permission: 字典,定义权限,字典类型,分别定义get
和post
的权限,permission的value除了权限定义字符串外,还有几个保留字段,分别是superuser
、login_user
、anonymous_user
,详细用法如下
superuser
:仅超级管理员有权限login_user
:所有登录用户都有权限anonymous_user
:所有人都可以访问,无论是否登录当请求包含字段参数时,则会根据字段参数过滤数据,例如请求:?project=ops-coffee&format=json
,则最终的QuerySet是self.model.objects.all().filter(project="ops-coffee")
当请求包含sort参数时,可以根据sort参数的值进行排序,例如请求:?sort=sortnum
,则最终的QuerySet是self.model.objects.all().orderby('sortnum')
,请求的参数sort会和view中定义的变量orderby整合,具体的是sort+orderby取交集,sort在前,orderby在后,例如前端请求是?sort=sortnum
,而view配置了orderby参数是orderby=[-id]
,则最终的QuerySet会是self.model.objects.all().orderby('sortnum','-id')
,sort一次可以传多个,多个用逗号隔开,例如?sort=sortnum,name,age
当强求包含start和length参数时,可以根据start和length参数的值进行数据切片,例如请求:?start=1&length=10
,则最终的QuerySet是self.model.objects.all()[1:11]
当前端是datatables异步发来的请求时则会返回datatables所需要的最终格式,包含draw
、recordsTotal
、recordsFiltered
、data
{
"draw": int(request.GET.get('draw')),
"recordsTotal": _recordsTotalCount,
"recordsFiltered": eval(_queryset + '.count()'),
"data": _table_data
}
当查询条件比较复杂,通过filter
无法满足需求时,可以使用get_queryset
自定义方法来定义更为复杂的查询条件。get_queryset
返回一个queryset的字符串,这个字符串会跟后续的查询条件等拼接
class TasklogList(ListCreateView):
model = TaskLog
orderby = ['-id']
template = 'engine/tasklog.index.html'
permission = {'get': 'engine.tasklog_select'}
@staticmethod
def get_queryset(request):
tasks = [i.id for i in get_tasks_for_user(request)]
return 'self.model.objects.filter(task_id__in={})'.format(tasks)
当权限定义比较复杂,通过permission
无法满足需求时,可以使用valid_permission
自定义方法来定义更为复杂的权限验证。valid_permission
返回一个布尔值,根据这个布尔值来确定是否有权限,如果为True则有权限,为False则无权限
class TaskDetail(RetrieveUpdateDestroyView):
model = Task
def valid_permission(self, request, pk):
return True if self.model.objects.get(id=pk) in get_tasks_for_user(request) else False
RetrieveUpdateDestroyView用来实现object(行)级别的操作,包括获取某条数据的详情、修改某条数据或时删除某条数据,分别对应了get
、put
和delete
三个方法,用法如下:
class TaskDetail(RetrieveUpdateDestroyView):
model = Task
template = 'engine/task.detail.html'
permission = {'get': 'engine.task_select', 'put': 'engine.task_change', 'delete': 'engine.task_change'}
接收三个方法,分别是get
、put
和delete
get: 获取单条数据
put: 更新单条数据
delete: 删除单条数据,当model中存在is_deleted
字段时,则会进行逻辑删除,也就是仅修改is_deleted
字段为True,并不会实际从数据库中删除数据
接收几个变量,分别是:model
、template
、permission
、project_filter
model: 要操作的model
template: 字符串,定义detail模板,如果模板为空则返回JsonResponse,如果模板不为空则返回render并附带data
变量,可直接在模板中使用,通过{{ data.field_name }}
来获取数据
permission: 字典,定义权限,定义get
、put
和delete
的权限,permission的value除了List中定义的superuser
、login_user
、anonymous_user
三个保留字段外,还多了个保留字段owner
,当权限值为owner
时仅数据创建者有操作权限,前提是model中要有create_user
字段,create_user
字段记录的就是数据创建者
project_filter: 布尔值,定义是否根据project过滤,默认为True,当表字段中存在project字段时,则在操作数据前会先判断用户是否有当前项目的权限,用户当前project仅从要操作的数据字段里获取