【问题标题】:django template system, calling a function inside a modeldjango模板系统,调用模型内的函数
【发布时间】:2010-11-22 22:07:52
【问题描述】:

我想从我的模型中调用一个函数,例如:

class ChannelStatus(models.Model):
 ..............................
 ..............................

    def get_related_deltas(self,epk):
        mystring = ""
        if not self.get_error_code_delta(epk):
            return mystring
        else:
            for i in self.get_listof_outage():
                item = i.error_code.all()
                for x in item:
                    if epk == x.id:
                        mystring= mystring +" "+str(i.delta())
        return mystring         

当我想从模板中调用它时: 假设在渲染时,我将 channel_status_list 传递为

channel_status_list = ChannelStatus.objects.all()

{% for i in channel_status_list %}
  {{ i.get_related_deltas(3) }}
{% endfor %}

这不起作用,我可以调用一个什么都不消耗的函数,但是如果它有参数,我找不到该怎么做

干杯

【问题讨论】:

    标签: python django django-models django-templates


    【解决方案1】:

    您不能使用模板中的参数调用函数。您只能在视图中执行此操作。或者你可以写一个custom template filter,它可能看起来像这样:

    @register.filter
    def related_deltas(obj, epk):
        return obj.get_related_deltas(epk)
    

    所以现在您可以在模板中执行此操作:

    {% for i in channel_status_list %}
      {{ i|related_deltas:3 }}
    {% endfor %}
    

    【讨论】:

    • 您好,非常感谢您的备份!我收到“related_deltas 需要 1 个参数,提供 0 个”错误。我正在按照你说的做。问候
    • 嗯,应该可以。你能发布完整的回溯吗(可能像 dpaste.com 这样的地方而不是这里)?
    • 这似乎是另一个错误,可能是由{{ forloop.parentloop.counter0||add:"5" }} 中的双竖线字符引起的。
    • 其实在我的模板中是{{ forloop.parentloop.counter0|add:"5" }},显示为"||"真的很奇怪。
    • 大家好,代码中定义的related_deltas 函数在哪里?我收到名称错误:当我尝试将其放在我的视图中时,名称“注册”未定义。
    【解决方案2】:

    另一个选项是定义一个属性。 见http://adam.gomaa.us/blog/2008/aug/11/the-python-property-builtin/

    您编写的函数几乎可以做任何您想做的事情。 您将其设为只读属性。 您从模板中调用该属性。

    等等!!!!

    【讨论】:

    • 这毫无意义...... Django 模板系统已经允许像调用属性一样调用方法(只要方法不接受任何参数)
    【解决方案3】:

    如果您发现到处都有太多的属性,或者您编写的每个其他方法都有一个模板过滤器,IRC 上建议了另一个解决方案,感谢@FunkyBob。这有点好,呃,时髦,但在某些情况下很好。

      class MethodProxy(object):
            """For consolidating into 1 method the calling of methods with various single args
            (suitable dictionary keys)
    
            class MyModel(models.Model):
                ...
    
                def magic(self, value):
                    # Free the ponies
    
                def thing(self):
                    return MethodProxy(self.magic)
    
            # Usage
            >>> m = MyModel()
            ...
            >>> m.thing['value'] == m.magic('value')
    
            # template
            {{ m.thing.value }}
    
            """
    
            def __init__(self, method):
                self.method = method
            def __getitem__(self, key):
                return self.method(key)
    

    【讨论】:

      【解决方案4】:

      如果方法不需要任何参数,您可以使用@property 装饰器并在模板中正常访问它。

      class ChannelStatus(models.Model):
          ...
          @property
          def function_you_want_as_property(self):
              mystring = ""
              ...
      

      【讨论】:

      • 问题中不是这种情况,只要它们没有任何参数,Django 也可以无缝地使用属性或方法。
      • @property 不需要
      • 能否在模板中添加使用示例?
      【解决方案5】:

      对于 > 1 个参数,使用 simple tags:

      @register.simple_tag
      def related_deltas(obj, epk, second_arg):
          return obj.get_related_deltas(epk, second_arg)
      

      模板:

      {% for i in channel_status_list %}
        {% related_deltas i 3 4 %}
      {% endfor %}
      

      (注意语法从{{{%

      可以采用位置参数(例如related_deltas i 3 second_arg=4 debug=true)。

      【讨论】:

        猜你喜欢
        • 2021-09-21
        • 2011-01-03
        • 2011-04-07
        • 2010-12-24
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多