高手接招! 在django的通用视图里面做判断

我用django的通用视图代码是这样的:

class IndexView(BaseView, ListView):
    ismobile = True
    if ismobile:
        template_name = "m/index.html"
    else:
        template_name = 'index.html'
    context_object_name = 'article_list'
    paginate_by = settings.PAGE_NUM  # 分页--每页的数目

    def get_queryset(self):
        article_list = Article.objects.filter(status=0)
       
        return article_list

    def get_context_data(self, **kwargs):
        # 轮播
        kwargs['home']= True
        return super(IndexView, self).get_context_data(**kwargs)
        

大家可以帮我看下,我代码的第一句是ismobile = True意思就是判断是不是手机端方访问的.
我的目的是想改成通过requests来判断,比如把代码改成这样

class IndexView(BaseView, ListView):
    #手机访问,用手机模板
    if 'm.maidu.com' in self.request.get_host():
        template_name = "m/index.html"
    
    电脑访问用电脑模板
    else:
        template_name = 'index.html'
.......

但是代码直接这样写会出错,会提示self不存在,我想下,如何优雅的解决这个问题?

阅读 4k
4 个回答

我的理解是你想根据不同的请求类型渲染不同的模板么?可以复现 get_template_names 方法:

class IndexView(BaseView, ListView):
    context_object_name = 'article_list'
    paginate_by = settings.PAGE_NUM  # 分页--每页的数目

    def get_template_names(self):
        ismobile = 从请求 self.request 中获得值
        template_names = super().get_template_names()
        if ismobile:
            template_name = "m/index.html"
        else:
            template_name = 'index.html'
        template_names.insert(0, template_name )
        return template_names

这个方法来自 TemplateResponseMixin,用于获取 django 视图渲染的模板,建议看一下 ListView 的源代码就清楚了。

试试这样的,不是用self,你类中应该写一个方法,这个方法其中有一个参数 是request

from django.utils.deprecation import MiddlewareMixin

class MultipleProxyMiddleware(MiddlewareMixin):

FORWARDED_FOR_FIELDS = [
    'HTTP_X_FORWARDED_FOR',
    'HTTP_X_FORWARDED_HOST',
    'HTTP_X_FORWARDED_SERVER',
]

def process_request(self, request):
    """
    Rewrites the proxy headers so that only the most
    recent proxy is used.
    """
    for field in self.FORWARDED_FOR_FIELDS:
        if field in request.META:
            if ',' in request.META[field]:
                parts = request.META[field].split(',')
                request.META[field] = parts[-1].strip()

django的CBV本身是有get()方法的,get(self, request, args, *kwargs),这里面是有你想要的request参数的,其实首先要搞清楚你的Class View的调用顺序。给你提供一个有关django CBV的连接,我想里面会帮助到你。
https://ccbv.co.uk/

继承View类
在class IndexView(BaseView, ListView):添加View,即:
class IndexView(BaseView, ListView,View):就可以调用self.request

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题