2015-09-17 2 views
2

В этом проекте django есть много моделей, и мы хотим добавить пользовательский набор запросов и диспетчер к каждому, используя queryset.as_manager, не указывая его в каждом модель вручную.Как добавить персонализированный менеджер для моделирования в django

Все запросы/менеджеры организованы в параллельной структуре каждой модели в папке manager.py в отдельных приложениях django.

Поскольку менеджеры являются атрибутом уровня класса, добавление их в init не работает, а django делает довольно симпатичное мета-программирование, так что это правильный способ сделать это? Оба варианта Django 1.7 и 1.8 являются приемлемыми. Благодаря

(я получаю, что вещий способ явно лучше, чем неявное, но это, кажется, аа много сырого кода здесь так есть мета способ сделать это.)

ответ

1

Вы могли бы написать фабричную функцию для создать proxy models как этот:

def model_with_queryset(model_class, queryset_class): 
    class Proxy(model_class): 
     objects = queryset_class.as_manager() 
     class Meta: 
      proxy = True 
      app_label = model_class._meta.app_label 
    return Proxy 

Здесь model_class бы любая модель, которую хотите изменить QuerySet на.

Затем можно создать классы модели динамически:

SomeModelWithSomeQS = model_with_queryset(SomeModel, SomeQS) 

и использовать их, как и любой другой (прокси) модели.

0

Джанго-путь будет использовать db.signals.class_prepared сигнал и черпать вдохновение из django.db.managers.ensure_default_manager() правильно добавить менеджера класса (в основном с использованием model.add_to_class(), чтобы убедиться, что contribute_to_class() метод менеджеров является правильно ссылаться). Затем вам нужно будет написать некоторую функцию утилиты для получения соответствующего набора запросов для данного класса модели.

Или вы могли бы написать свой собственный метакласс (на основе django.db.models.base.ModelBase) и класс модели (используя свой пользовательский метакласс) и сделать все классы моделей наследуемыми от него.

Это, как говорится, вам действительно нужно иметь много моделей даже рассмотреть любого из этих решений, как экономически обоснованные ...

+0

Для дальнейшего (метакласса) разработать вторую идею, так как мы уже есть все наши классы моделей, наследующие от общего базового класса модели (который был пуст для начала) только для такого типа вещей. Проблема, с которой я сталкиваюсь, состоит в том, что метакласс django на самом деле не поддерживает подклассы ... или я не делая этого правильно. Позаботьтесь написать небольшой фрагмент или псевдокод для подхода 2? Его корпоративное приложение, я бы сказал, 100 моделей или около того ... достаточно экономичный, я думаю :) Также сохраняет изменения в централизованном и уменьшает количество плиты котла – eskhool

+1

Мне удалось выяснить это, используя код метакласса django в качестве источника , Я могу написать это как свой собственный ответ и принять его, однако, как и в протоколе SO, первая возможность для решения должна быть вашей:) ... Если вы поместите код вверх, я с радостью соглашусь с ним как с ответом или Я напишу свое. Дайте мне знать в любом случае. – eskhool

+0

@eskhool, так как вы получили работу, не стесняйтесь публиковать свой ответ. У меня нет времени писать рабочий пример django 1.7+ прямо сейчас;) –