可以在django.contrib.admindocs中获取模型属性的文档吗?

时间:2018-02-14 18:01:12

标签: python django

是否可以使用django.contrib.admindocs在管理文档中显示模型属性(如下所示)?

  class MyModel(models.Model):
      name = models.CharField(max_length=200)
      public = models.BooleanField(default=False)
      date_approved = models.DateTimeField(null=True, blank=True)

      @property
      def status(self):
      """
        returns the status of object
      """
      if self.date_approved and self.public:
        return "Public"
      elif self.public:
        return "Pending Approval"
      else:
        return "Private"

1 个答案:

答案 0 :(得分:1)

我找到的唯一解决方案就是修补admindocs

在文件django/contrib/admindocs/views.py中找到方法ModelDetailView.get_context_data。有一个部分收集模型方法,但跳过属性,因为它们不是方法。因此,我们需要(1)向条件添加属性,以及(2)将属性附加到字段列表。

# Gather model methods.
for func_name, func in model.__dict__.items():
    #
    # CHANGE 1: add isinstance(func, property) to the condition
    #
    # if inspect.isfunction(func): # old line
    if inspect.isfunction(func) or isinstance(func, property):
        try:
            for exclude in MODEL_METHODS_EXCLUDE:
                if func_name.startswith(exclude):
                    raise StopIteration
        except StopIteration:
            continue
        verbose = func.__doc__
        if verbose:
            verbose = utils.parse_rst(utils.trim_docstring(verbose), 'model', _('model:') + opts.model_name)

        #
        # CHANGE 2: If this is a property, show it as a 'field'
        #
        if isinstance(func, property):
            fields.append({
                'name': func_name,
                'data_type': get_return_data_type(func_name),
                'verbose': verbose or '',
            })
        # Else if a method has no arguments, show it as a 'field', otherwise
        # as a 'method with arguments'.
        elif func_has_no_args(func) and not func_accepts_kwargs(func) and not func_accepts_var_args(func):
            fields.append({
                'name': func_name,
                'data_type': get_return_data_type(func_name),
                'verbose': verbose or '',
            })
        else:
            arguments = get_func_full_args(func)
            # Join arguments with ', ' and in case of default value,
            # join it with '='. Use repr() so that strings will be
            # correctly displayed.
            print_arguments = ', '.join([
                '='.join(list(arg_el[:1]) + [repr(el) for el in arg_el[1:]])
                for arg_el in arguments
            ])
            methods.append({
                'name': func_name,
                'arguments': print_arguments,
                'verbose': verbose or '',
            })