2017-12-10 23 views
0

파이썬에서 "ORM like"동작을 구현하려고합니다. 이렇게하려면 Model 클래스가 있고 모든 종류의 하위 클래스를 생성하려고합니다. 내 문제는 내 하위 클래스 인스턴스의 특성을 나열하려고 할 때입니다.파이썬에서 서브 클래스 인스턴스의 속성을 나열하십시오.

class Model: 
    def __init__(self): 
     self.className = type(self).__name__ 

    def listAttributes(self): 
     from modules.users.user import User 
     instance = User() 
     meta = vars(instance) 

그리고 사용자의 서브 클래스 : 여기 내 모델 클래스 I는 사용자 인스턴스에서 listAttributes 메소드를 호출 할 때

class User(models.Model): 
    name = models.FieldChar() 
    password = models.FieldChar() 
    age = models.FieldInteger() 

, 나는 내가 무엇을 기대하지 않지만, 아마 내가 다음과 같아야합니다 : 메타 변수에는 클래스 이름 만 포함됩니다. 여기에 내가 메소드를 호출하는 방법은 다음과 같습니다

from modules.users import user 
user = user.User() 
user.listAttributes() 

같은 행동을 나는 사용자의 listAttributes 방법()를 오버라이드 (override) 할 때 :

def listAttributes(self): 
    meta = vars(self) 
    print(meta) 

내가 호출되는 객체의 속성을 나열하는 방법이 있나요 listAttributes 메서드?

조명에 감사드립니다!

class Model(object): 
    @classmethod 
    def listAttributes(cls): 
     return [ 
      a for a in dir(cls) if not 
      callable(getattr(cls, a)) and not 
      a.startswith("__") 
     ] 

당신이 당신 "필드"유형 인 특성 (FieldChar, FieldInt을 ...) 가지고 싶다면 다음 당신에게 :

답변

1

다음 당신의 listAttributes의 방법 A classmethod하고 시도 할 수 필드라고하는 기본 클래스를 만들 수 있습니다. ModelField를 선택하고이 기본 유형에 대해 속성을 확인하십시오.

class Model(object): 
    @classmethod 
    def listAttributes(cls): 
     attributes = [] 
     for a in dir(cls): 
      if ((not callable(getattr(cls, a)) and not 
       a.startswith("__") and 
       getattr(cls, a).__class__.__bases__[0] == ModelField)): 
       attributes.append(a) 

이름 대신 객체를 반환 할 수도 있습니다. 또는 Model 클래스의 dict에 객체를 추가하면 코드에서 쉽게 사용할 수 있습니다.

class ModelField(object): 
    ... 

class IntField(ModelField): 
    ... 

class Model(object): 
    id = IntField(pk=True) 

    def __init__(self, *args, **kwargs): 
     try: 
      self.modelFields 
     except AttributeError: 
      self.__class__.introspect() 
     for key, modelfield in self.modelFields.items(): 
      setattr(self, key, kwargs.get(key, None)) 

    @classmethod 
    def introspect(cls): 
     cls.modelFields = {} 
     for a in dir(cls): 
      if ((not callable(getattr(cls, a)) and not 
       a.startswith("__") and 
       getattr(cls, a).__class__.__bases__[0] == ModelField)): 
       cls.modelFields[a] = getattr(cls, a) 

그런 다음 내가 modelFields의 DICT를 설정하고 가령이 딕셔너리를 사용하는 cls.introspect을 사용 :이처럼 내 ORM이 건설 ModelField 클래스의 속성을 사용하여 db 테이블을 자동 생성하거나 쿼리를 생성합니다.

+0

전적으로 찾고있는 내용입니다. 나는 파이썬에서 그 수준의 인트로피 션 레벨에 대한 희망을 잃었다. 그 철저한 대답을위한 고맙습니다. – Glandalf313