【问题标题】:Django, how to reuse views code in other views and templateDjango,如何在其他视图和模板中重用视图代码
【发布时间】:2020-05-05 19:13:22
【问题描述】:

我是 django 的新手,我想知道是否可以在 views.py 中重用代码和注释输出。

我创建了许多新的注释输出,我想重复使用这些输出来找出带有图表和关键指标的仪表板。我不喜欢重写所有代码,因为我不会遵循 DRY 原则。

广告示例我有以下视图,在其他视图中重用此代码的最佳方法是什么?

def conto_economico(request):
    # Creazione tabella materie prime, sussidiarie, di consumo e merci
    defaults = list(0 for m in range(12))
    elements = dict()
    for conto_id, year, month, totale in(Materiale.objects.values_list('conto__nome', 'data__year', 'data__month').annotate(totale=ExpressionWrapper(Sum(F('quantita') * F('prezzo')),
        output_field=FloatField())).values_list('conto__nome', 'data__year', 'data__month', 'totale').order_by("conto_id")) :
        if conto_id not in elements.keys():
            elements[conto_id]=list(defaults)
        index=month-1
        elements[conto_id][index]=totale

    total_elements={'Per materie prime, sussidiarie, di consumo e di merci': [sum(t) for t in zip(*elements.values())],}

    context= {
        'elements': elements,
        'total_elements':total_elements,
    }

    return render(request, 'conto_economico/conto_economico.html', context)

【问题讨论】:

    标签: django django-models django-forms django-views django-templates


    【解决方案1】:

    对于views.py 文件,最好使用装饰器。在另一个问题中进一步解释了here

    对于模板,使用{% include %} 标签。例如,您可以在另一个文档(例如 HTML)中编写代码的 sn-ps,然后使用 {% include '_example.html' %} 模板标签将该代码插入另一个模板中。在这种情况下,另一个文件名为 _example.html

    编辑 1:

    要在其他函数的模板中使用相同的上下文,我们需要在特定的 Django 应用程序中创建一个context_processor.py 文件。这是一个 Django 约定。当我们需要为所有 Django 应用程序的所有模板提供全局可用的东西时,上下文处理器很方便。

    上下文处理器通常返回一个字典,该字典被添加到request 上下文中。

    您的代码在概念上看起来像这样,您可能需要调试代码是否有错误-

    # <app_name>/context_processor.py (this is the same folder where the views.py)
    
    from .models import Materiale
    
    def conto_economico(request):
        # Creazione tabella materie prime, sussidiarie, di consumo e merci
        defaults = list(0 for m in range(12))
        elements = dict()
        for conto_id, year, month, totale in(Materiale.objects.values_list('conto__nome', 'data__year', 'data__month').annotate(totale=ExpressionWrapper(Sum(F('quantita') * F('prezzo')),
            output_field=FloatField())).values_list('conto__nome', 'data__year', 'data__month', 'totale').order_by("conto_id")) :
            if conto_id not in elements.keys():
                elements[conto_id]=list(defaults)
            index=month-1
            elements[conto_id][index]=totale
    
        total_elements={'Per materie prime, sussidiarie, di consumo e di merci': [sum(t) for t in zip(*elements.values())],}
    
        #context= {
            #'elements': elements,
            #'total_elements':total_elements,
        #}
    
        #return render(request, 'conto_economico/conto_economico.html', context)
        return dict(elements=elements, total_elements=total_elements)
    

    注意事项-

    • 我从未在context_processor.py 中的dict() 中使用多个变量。在这种情况下,我们通过了两个。您可能需要注意任何错误。

    然后在项目的settings.py文件中提供这个上下文-

    # settings.py
    
    TEMPLATES = [
        {
            'BACKEND': 'django.template.backends.django.DjangoTemplates',
            'DIRS': [],
            'APP_DIRS': True,
            'OPTIONS': {
                'context_processors': [
                    'django.template.context_processors.debug',
                    'django.template.context_processors.request',
                    'django.contrib.auth.context_processors.auth',
                    'django.contrib.messages.context_processors.messages',
                    'app_name.context_processors.conto_economico', # change the 'app_name' to the actual app name.
                ],
            },
        },
    ]
    

    现在两个上下文变量elementstotal_elements 应该可用于所有模板。不再需要将def conto_economico函数的代码复制粘贴到views.py中的其他函数中。

    进一步阅读-https://dev.to/harveyhalwin/using-context-processor-in-django-to-create-dynamic-footer-45k4

    【讨论】:

    • @FA 感谢您的回答。我非常感谢您的回答,但我不知道是否是找出我需求的最佳方法。我在问题中添加了我的视图代码的 sn-ps,以更好地解释我的需求。
    • 你想重用整个函数conto_economico还是某个部分?如果某个部分,你想重复使用哪一部分?
    • 我只想重用上下文结果,因为这个视图给了我一个表格,我想创建另一个视图来找出一个仪表板,其中包含使用相同上下文的图表
    • @FedericoDeMarco 我已经更新了答案。关于使用上下文处理器要记住的另一件事是,尽可能少地使用它,因为它会给 request 带来负载。
    猜你喜欢
    • 1970-01-01
    • 2011-07-07
    • 2012-05-26
    • 2014-03-11
    • 1970-01-01
    • 2014-09-16
    • 1970-01-01
    • 1970-01-01
    • 2019-03-14
    相关资源
    最近更新 更多