당신은 멋쟁이, 우리는 장고쟁이~

0%

Django Models 20편 - Model 상속 (Proxy models - 2)

Model Inheritance proxy models - 2


Base class restrictions


프록시 모델은 하나의 모델 클래스 (abstract 가 아닌것)을 상속 받아야 합니다


하지만, 다중의 모델 (abstract 가 아닌것)들을 상속 받을수 없습니다.

프록시 모델은, 다른 데이터 베이스 테이블들에 존재하는 행(row) 들끼리 연결을 지원하지 않습니다.


프록시 모델은 abstract 모델이 어떤 모델 필드도 정의하지 않는다는 전제하에, 여러개의 abstract 모델 클래스들을 상속 받을수 있습니다.


프록시 모델은 또한, 공통된 부모 클래스 (단, abstract 클래스가 아니여야 함)를 공유한다는 전제하에, 몇개라도 프록시 모델들을 상속 받을수 있습니다.


Proxy model managers


프록시 모델에 어떤 model manager 도 지정하지 않는다면, 부모 모델의 manager 를 상속 받습니다.


만약 프록시 모델에 manager 를 정의 한다면, 정의된 manager 가 기본값이 됩니다.


물론, 어떤 manager 든지 부모 클래스에 정의된 manager 도 여전히 사용 가능합니다.


이전 포스팅에서 진행한 예시에 이어서, Person 모델의 쿼리에서 사용되는 기본 manager 를 바꿀수 있습니다.


1
2
3
4
5
6
7
8
9
10
11
12
from django.db import models

class NewManager(models.Manager):
# ...
pass


class MyPerson(Person):
objects = NewManager()

class Meta:
proxy = True

만약 새로운 manager 를 기존에 존재하는 기본값을 바꾸지 않고 프록시에 추가하고 싶으면, custom manager 문서에 나와 있는 기술들을 사용해서 바꿀수 있습니다.


새로운 manager 를 가지고 있는 클래스를 생성하고, 기본 베이스 클래스 뒤에, 생성한 클래스를 상속 시켜 주면 됩니다.


1
2
3
4
5
6
7
8
9
10
# 새로운 Manager 를 위한 Abstract 클래스를 생성해줍니다.
class ExtraManagers(models.Model):
secondary = NewManager()

class Meta:
abstract = True

class MyPerson(Person, ExtraManagers):
class Meta:
proxy = True


프록시 상속과 관리되지않은 모델의 차이점


프록시 모델 상속은 Meta 클래스에 managed 속성을 사용한, 관리되지 않은 모델을 생성하는것과 비슷해 보일지 모릅니다.


조심스럽게 Meta.db_table 을 설정하여, 기존에 존재하는 모델의 그림자 같은 관리되지 않은 모델을 생성할수 있고, 파이썬 메서드도 추가할수 있습니다.


하지만, 그것은 매우 반복적이고 깨지기 쉬운 구조 입니다. 수정할때 마다, 모든 복사본들을 동기화 해야 하기 때문입니다.


한편으로는, 프록시 모델들은 정확하게 프록싱 하는 기존 모델의 동작 처럼 동작하게 만들어 졌습니다. 프록시 모델은 언제나 부모 모델과 동기화 되어 있습니다 (직접 필드와 메니져들을 부모에게서 상속 받기 때문).


보통 법칙들은

  1. 기존 모델 혹은 데이터베이스를 미러링 하고, 모든 오리지널 데이터베이스 테이블 열들을 원하지 않을때, Meta.mangled=False 를 사용해 줍니다. 이 옵션은 데이터베이스 뷰들을 모델링 할때와 Django 로 제어되지 않는 테이블들을에 유용합니다.
  1. 만약 모델의 파이썬 동작만 바꾸고 싶은데, 같은 필드들을 오리지널과 같이 유지하고 싶을때, Meta.proxy=True 로 설정해 줍니다. 이 설정은, 데이터가 저장될때, 프록시 모델이 정확한 오리지널 모델 저장구조의 복사본이 됩니다.