94

我的主管的指示:“我想避免在models.py.

我觉得这是错误的方法。我觉得为了保持文件小而将逻辑排除在模型之外是一个坏主意。如果模型中的逻辑是最好的,那么无论文件大小如何,这都是它真正应该去的地方。

那么有没有一种简单的方法来使用包含?在 PHP 中,我想向主管建议我们只models.py包含()来自其他地方的模型类。从概念上讲,这将允许模型具有我们想要的所有逻辑,同时通过增加文件数量来减小文件大小(这会导致更少的修订控制问题,如冲突等)。

那么,有没有一种简单的方法可以从 models.py 文件中删除模型类,但仍然可以让模型与所有 Django 工具一起使用?或者,对于“大型”models.py 文件的一般问题,是否有完全不同但优雅的解决方案?任何输入将不胜感激。

4

3 回答 3

113

模型类包含对模型进行操作的方法是很自然的。如果我有一个带有方法的 Book 模型,book.get_noun_count()那就是它所属的地方——我不想写“ get_noun_count(book)”,除非该方法实际上本质上属于某个其他包。(它可能——例如,如果我有一个使用“ get_amazon_product_id(book)”访问亚马逊 API 的包。)

当 Django 的文档建议将模型放在一个文件中时,我感到畏缩,我从一开始就花了几分钟来弄清楚如何将它拆分为适当的子包。

site/models/__init__.py
site/models/book.py

__init__.py好像:

from .book import Book

所以我仍然可以写“从 site.models 导入书”。


以下内容仅适用于 Django 1.7 之前的版本,请参阅 https://code.djangoproject.com/ticket/3591

唯一的技巧是,由于 Django 中的一个错误,您需要显式设置每个模型的应用程序:它假定应用程序名称是模型路径中的倒数第三个条目。“site.models.Book”的结果是“site”,这是正确的;“site.models.book.Book”使它认为应用程序名称是“models”。这对 Django 来说是一个非常讨厌的 hack。它可能应该在已安装应用程序列表中搜索前缀匹配。

class Book(models.Model):
    class Meta: app_label = "site"

您可能可以使用基类或元类来概括这一点,但我还没有为此烦恼。

于 2009-07-21T18:02:38.617 回答
65

Django 旨在让您构建许多小应用程序而不是一个大应用程序。

每个大型应用程序内部都有许多小应用程序在努力争取免费。

如果你models.py觉得自己很大,那么你做的太多了。停止。放松。分解。

寻找更小的、可能可重复使用的小型应用程序组件或片段。您不必实际重用它们。只需将它们视为潜在可重复使用的。

考虑您的升级路径并分解您将来可能想要替换的应用程序。您不必实际替换它们,但您可以将它们视为一个独立的编程“模块”,将来可能会被更酷的东西取代。

我们有大约十几个应用程序,每个model.py不超过 400 行代码。他们都非常关注不到大约六个离散类定义。(这些不是硬性限制,它们是对我们代码的观察。)

我们很早就并且经常分解。

于 2009-07-21T17:32:43.110 回答
6

我无法完全了解您可能遇到的许多可能问题中的哪一个。以下是一些可能的答案:

  • 同一文件中的多个模型

    将它们放入单独的文件中。如果存在依赖关系,请使用 import 拉入其他模型。

  • models.py 中无关的逻辑/实用功能

    将额外的逻辑放入单独的文件中。

  • 从数据库中选择一些模型实例的静态方法

    在单独的文件中创建一个新的Manager 。

  • 与模型明显相关的方法

    save、__unicode__ 和 get_absolute_url 是示例。

于 2009-07-21T18:42:12.033 回答