zoukankan      html  css  js  c++  java
  • Django+xadmin打造在线教育平台(十)

    目录

    在线教育平台(一)      在线教育平台(二)

    在线教育平台(三)      在线教育平台(四)

    在线教育平台(五)      在线教育平台(六)

    在线教育平台(七)      在线教育平台(八)

    在线教育平台(九)      在线教育平台(十)

    代码

    github下载

    教程

    学习自慕课网-使用python3.x与Django2.0.1开发的在线教育平台

    十四、xadmin的进阶开发

    14.1.权限管理

    (1)用户权限

    超级用户拥有所有权限,其它添加的用户默认没有任何权限

    进后台添加一个用户“Editor1”,勾上“职员状态”后,这个用户才可以登录进后台,默认没添加权限的用户登录到后台的情况如下:

    接下来,为用户Editor1添加查看课程和查看章节的权限

     再刷新可以看到,有了查看课程和章节的权限了

     (2)组的权限

     添加一个组“编辑部门”,赋予如下权限 :

     把刚才的用户“Editor1”加入到“编辑部门”这个组,然后看用户现在的权限如下:

    组里面的成员不但拥有自己本身的权限外,还会拥有组的权限

    14.2.自定义icon

     xadmin的图标采用的是第三方css样式“font awesome”,我们可以进官网下载最新的样式替代原本的,下载地址:http://www.fontawesome.com.cn/

    下载完后把里面的“css”和“fonts”两个文件夹拷贝到xadmin的源码(路径:xadmin/static/vendor/font-awesome)里面

    使用方法:

    以course为例

    (1)进官网找到图标的样式

    (2)course/adminx.py使用

    # Course的admin管理器
    class CourseAdmin(object):
        '''课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students']
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']
        list_filter = [ 'name','desc','detail','degree','learn_times','students']
        model_icon = 'fa fa-book'

    再在后台刷新(ctrl+F5),就可以看到图标了

     

    14.3.默认排序、只读字段和不显示的字段

    课程:

    • 按点击数倒序排序
    • 点击数不能编辑
    • 不显示收藏人数
    # Course的admin管理器
    class CourseAdmin(object):
        '''课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students']   #显示的字段
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']             #搜索
        list_filter = [ 'name','desc','detail','degree','learn_times','students']    #过滤 
        model_icon = 'fa fa-book'            #图标
        ordering = ['-click_nums']           #排序
        readonly_fields = ['click_nums']     #只读字段,不能编辑
        exclude = ['fav_nums']               #不显示的字段

    14.4.inlines添加数据

     目前在添加课程的时候没法添加章节和课程资源,我们可以用inlines去实现这一功能

    class LessonInline(object):
        model = Lesson
        extra = 0
    
    
    class CourseResourceInline(object):
        model = CourseResource
        extra = 0
    
    
    #在CourseAdmin中使用inlines添加上面两个的方法
    class CourseAdmin(object):
        inlines = [LessonInline,CourseResourceInline]    #增加章节和课程资源

    效果如下:

    再添加课程的时候,可以直接添加章节和课程资源

    14.5.一张表分两个Model来管理

    课程里面分为轮播课程和不是轮播课程两种类型,我们可以分开来管理

    (1)在course/models.py里面新建一个Model

    class BannerCourse(Course):
        '''显示轮播课程'''
        class Meta:
            verbose_name = '轮播课程'
            verbose_name_plural = verbose_name
            #这里必须设置proxy=True,这样就不会再生成一张表,同时还具有Model的功能
            proxy = True

    (2)course/adminx.py

    from .models import BannerCourse
    
    class CourseAdmin(object):
        '''课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students']   #显示的字段
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']             #搜索
        list_filter = [ 'name','desc','detail','degree','learn_times','students']    #过滤
        model_icon = 'fa fa-book'            #图标
        ordering = ['-click_nums']           #排序
        readonly_fields = ['click_nums']     #只读字段
        exclude = ['fav_nums']               #不显示的字段
        inlines = [LessonInline,CourseResourceInline]    #增加章节和课程资源
    
        def queryset(self):
            # 重载queryset方法,来过滤出我们想要的数据的
            qs = super(CourseAdmin, self).queryset()
            # 只显示is_banner=True的课程
            qs = qs.filter(is_banner=False)
            return qs
    
    
    class BannerCourseAdmin(object):
        '''轮播课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students']
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']
        list_filter = [ 'name','desc','detail','degree','learn_times','students']
        model_icon = 'fa fa-book'
        ordering = ['-click_nums']
        readonly_fields = ['click_nums']
        exclude = ['fav_nums']
        inlines = [LessonInline,CourseResourceInline]
    
        def queryset(self):
            #重载queryset方法,来过滤出我们想要的数据的
            qs = super(BannerCourseAdmin, self).queryset()
            #只显示is_banner=True的课程
            qs = qs.filter(is_banner=True)
            return qs
    
    # 将管理器与model进行注册关联
    xadmin.site.register(Course, CourseAdmin)
    xadmin.site.register(BannerCourse, BannerCourseAdmin)

    后台:可以看到多了一个轮播课程,来达到分类管理的一个功能

     

    14.6.xadmin的其它常见功能

    (1)list_editable

    在列表页可以直接编辑的

    class CourseAdmin(object):
        list_editable = ['degree','desc']

     (2)自定义函数作为列显示

    course/models.py中

    class Course(models.Model):
        '
        '
        '
        def get_zj_nums(self):
            #获取课程的章节数
            return self.lesson_set.all().count()
        get_zj_nums.short_description = '章节数'   #在后台显示的名称

    course/adminx.py中

    class CourseAdmin(object):
        list_display = ['get_zj_nums']  #直接使用函数名作为字段显示

    效果:列表字段多了个“章节数”

    (3)显示自定义的html代码

    course/models.py中

    class Course(models.Model):
        .
        .
        .
        def go_to(self):
            from django.utils.safestring import mark_safe
            #mark_safe后就不会转义
            return mark_safe("<a href='https://home.cnblogs.com/u/derek1184405959/'>跳转</a>")
        go_to.short_description = "跳转"

    course/adminx.py中

    class CourseAdmin(object):
        list_display = ['go_to']

    效果:多了一个列表“跳转”,点击后跳转到上面定义的地址

    (4)refresh定时刷新工具

     course/adminx.py中

    class CourseAdmin(object):
        refresh_times = [3,5]           #自动刷新(里面是秒数)

    后台效果:

    可以选择3s或者5s自动刷新页面

    (5)字段联动

     应用场景:当添加一门课程的时候,希望课程机构里面的课程数 +1

     重写xadmin的save_models方法

    class CourseAdmin(object):
        .
        .
        .
        def save_models(self):
            # 在保存课程的时候统计课程机构的课程数
            # obj实际是一个course对象
            obj = self.new_obj
            # 如果这里不保存,新增课程,统计的课程数会少一个
            obj.save()
            # 确定课程的课程机构存在。
            if obj.course_org is not None:
                #找到添加的课程的课程机构
                course_org = obj.course_org
                #课程机构的课程数量等于添加课程后的数量
                course_org.course_nums = Course.objects.filter(course_org=course_org).count()
                course_org.save()
    # course/adminx.py
    
    import xadmin
    
    from .models import Course, Lesson, Video, CourseResource,BannerCourse
    from organization.models import CourseOrg
    
    class LessonInline(object):
        model = Lesson
        extra = 0
    
    
    class CourseResourceInline(object):
        model = CourseResource
        extra = 0
    
    
    # Course的admin管理器
    class CourseAdmin(object):
        '''课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students','get_zj_nums','go_to']   #显示的字段
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']             #搜索
        list_filter = [ 'name','desc','detail','degree','learn_times','students']    #过滤
        model_icon = 'fa fa-book'            #图标
        ordering = ['-click_nums']           #排序
        readonly_fields = ['click_nums']     #只读字段
        exclude = ['fav_nums']               #不显示的字段
        list_editable = ['degree','desc']
        # refresh_times = [3,5]                #自动刷新(里面是秒数范围)
        inlines = [LessonInline,CourseResourceInline]    #增加章节和课程资源
    
        def queryset(self):
            # 重载queryset方法,来过滤出我们想要的数据的
            qs = super(CourseAdmin, self).queryset()
            # 只显示is_banner=True的课程
            qs = qs.filter(is_banner=False)
            return qs
    
        def save_models(self):
            # 在保存课程的时候统计课程机构的课程数
            # obj实际是一个course对象
            obj = self.new_obj
            # 如果这里不保存,新增课程,统计的课程数会少一个
            obj.save()
            # 确定课程的课程机构存在。
            if obj.course_org is not None:
                #找到添加的课程的课程机构
                course_org = obj.course_org
                #课程机构的课程数量等于添加课程后的数量
                course_org.course_nums = Course.objects.filter(course_org=course_org).count()
                course_org.save()
    
    
    class BannerCourseAdmin(object):
        '''轮播课程'''
    
        list_display = [ 'name','desc','detail','degree','learn_times','students']
        search_fields = ['name', 'desc', 'detail', 'degree', 'students']
        list_filter = [ 'name','desc','detail','degree','learn_times','students']
        model_icon = 'fa fa-book'
        ordering = ['-click_nums']
        readonly_fields = ['click_nums']
        exclude = ['fav_nums']
        inlines = [LessonInline,CourseResourceInline]
    
        def queryset(self):
            #重载queryset方法,来过滤出我们想要的数据的
            qs = super(BannerCourseAdmin, self).queryset()
            #只显示is_banner=True的课程
            qs = qs.filter(is_banner=True)
            return qs
    
    class LessonAdmin(object):
        '''章节'''
    
        list_display = ['course', 'name', 'add_time']
        search_fields = ['course', 'name']
        #这里course__name是根据课程名称过滤
        list_filter = ['course__name', 'name', 'add_time']
    
    
    class VideoAdmin(object):
        '''视频'''
    
        list_display = ['lesson', 'name', 'add_time']
        search_fields = ['lesson', 'name']
        list_filter = ['lesson', 'name', 'add_time']
    
    
    class CourseResourceAdmin(object):
        '''课程资源'''
    
        list_display = ['course', 'name', 'download', 'add_time']
        search_fields = ['course', 'name', 'download']
        list_filter = ['course__name', 'name', 'download', 'add_time']
    
    
    # 将管理器与model进行注册关联
    xadmin.site.register(Course, CourseAdmin)
    xadmin.site.register(BannerCourse, BannerCourseAdmin)
    xadmin.site.register(Lesson, LessonAdmin)
    xadmin.site.register(Video, VideoAdmin)
    xadmin.site.register(CourseResource, CourseResourceAdmin)
    course/adminx.py全部代码

    14.7.增加富文本编辑器Ueditor

    (1)下载

    地址:https://github.com/twz915/DjangoUeditor3/

    解压后,把DjangoUeditor文件夹拷贝到项目目录下面

    注意:直接pip install DjangoUeditor的方法会出问题

    (2)settings中添加app

    INSTALLED_APPS = [
        'DjangoUeditor',
    ]

    (3)MxOnline/urls.py

       # 富文本编辑器url
        path('ueditor/',include('DjangoUeditor.urls' )),

     (4)course/models.py中Course修改detail字段

    class Course(models.Model):
        # detail = models.TextField("课程详情")
        detail = UEditorField(verbose_name=u'课程详情', width=600, height=300, imagePath="courses/ueditor/",
                              filePath="courses/ueditor/", default='')

    (5)xadmin/plugs目录下新建ueditor.py文件,代码如下

    import xadmin
    from xadmin.views import BaseAdminPlugin, CreateAdminView, ModelFormAdminView, UpdateAdminView
    from DjangoUeditor.models import UEditorField
    from DjangoUeditor.widgets import UEditorWidget
    from django.conf import settings
    
    
    class XadminUEditorWidget(UEditorWidget):
        def __init__(self, **kwargs):
            self.ueditor_options = kwargs
            self.Media.js = None
            super(XadminUEditorWidget,self).__init__(kwargs)
    
    
    class UeditorPlugin(BaseAdminPlugin):
    
        def get_field_style(self, attrs, db_field, style, **kwargs):
            if style == 'ueditor':
                if isinstance(db_field, UEditorField):
                    widget = db_field.formfield().widget
                    param = {}
                    param.update(widget.ueditor_settings)
                    param.update(widget.attrs)
                    return {'widget':XadminUEditorWidget(**param)}
            return attrs
    
        def block_extrahead(self, context, nodes):
            js  = '<script type="text/javascript" src="%s"></script>' %(settings.STATIC_URL + "ueditor/ueditor.config.js")
            js += '<script type="text/javascript" src="%s"></script>' %(settings.STATIC_URL + "ueditor/ueditor.all.min.js")
            nodes.append(js)
    
    xadmin.site.register_plugin(UeditorPlugin, UpdateAdminView)
    xadmin.site.register_plugin(UeditorPlugin, CreateAdminView)

    (6)xadmin/plugs/__init__.py里面添加ueditor插件

    PLUGINS = (
       'ueditor',
    )

    (7)course/adminx.py中使用

    class CourseAdmin(object):
        #detail就是要显示为富文本的字段名
        style_fields = {"detail": "ueditor"}

    (8)course-detail.html

    在模板中必须关闭Django的自动转义才能正常显示

    <div class="tab_cont tab_cont1">
         {% autoescape off %}
         {{ course.detail }}
         {% endautoescape %}
         </div>

    最终效果:

    后台编辑页面

     前端显示

     

     
     
     
  • 相关阅读:
    Chapter 03Using SingleRow Functions to Customize Output(03)
    Chapter 03Using SingleRow Functions to Customize Output(01)
    Chapter 04Using Conversion Functions and Conditional ExpressionsNesting Functions
    Chapter 04Using Conversion Functions and Conditional ExpressionsGeneral Functions
    Chapter 11Creating Other Schema Objects Index
    传奇程序员John Carmack 访谈实录 (zz.is2120)
    保持简单纪念丹尼斯里奇(Dennis Ritchie) (zz.is2120.BG57IV3)
    王江民:传奇一生 (zz.is2120)
    2011台湾游日月潭
    2011台湾游星云大师的佛光寺
  • 原文地址:https://www.cnblogs.com/gaidy/p/12106764.html
Copyright © 2011-2022 走看看