2017-01-30 11 views
0

SQLAlchemyデータベースに追加したいロープデータをクリーンアップしようとしています。だから、文字列を正しい列の長さに切り捨てます。setattrと__init__を使用してSQLAlchemyデータをクリーンアップする

これを実施するために、getattr()setattr()を使用するコンストラクタを作成しようとしました。しかし、何らかの理由で文字列が切り詰められていないなど..任意の提案?ピョートルDawidiukのおかげで、固定

class Property(Base): 
    """ 
    Property details as imported from various Council sources 
    """ 
    MAXPROPREFLEN = 20 
    MAXADDRESSLEN = 100 
    MAXDESCRIPLEN = 120 
    MAXPOSTCODELEN = 10 

    __tablename__ = 'properties' 
    id    = Column(Integer, primary_key=True) 
    PropertyRef = Column(String(MAXPROPREFLEN)) # Council reference, diffrerent from UPRN 
    AccountHolder = Column(String(MAXDESCRIPLEN)) 
    Address1  = Column(String(MAXADDRESSLEN)) 
    Address2  = Column(String(MAXADDRESSLEN)) 
    Address3  = Column(String(MAXADDRESSLEN)) 
    Address4  = Column(String(MAXADDRESSLEN)) 
    PostCode  = Column(String(MAXPOSTCODELEN), index=True) 
    UPRN   = Column(BigInteger) 
    Description = Column(String(MAXDESCRIPLEN)) 
    RV    = Column(Numeric(10, 0)) 
    Empty   = Column(Boolean) 
    LiableFrom  = Column(Date) 
    EmptySince  = Column(Date) 
    MEBID   = Column(Integer) # Key in MEB table if applicable 
    Authority  = Column(Integer) # Key in authorities table 

    def __init__(self, **kwargs): 
     """ 
     Ordinarily we wouldn't require a constructor, but the data from the 
     various LAs is of such poor quality and the Psycopg2 connector 
     so strict about types that we have to clean it up. So we need to 
     truncate overly long strings etc. 
     """ 
     for key, value in kwargs.items(): 
      if key == 'PropertyRef': 
       setattr(self, key, value[:Property.MAXPROPREFLEN] if value else None) 
      elif key == 'PostCode': 
       setattr(self, key, value[:Property.MAXPOSTCODELEN] if value else None) 
      elif key in ['AccountHolder', 'Description']: 
       if type(value) is str: 
        setattr(self, key, value[:Property.MAXDESCRIPLEN]) 
       else: 
        setattr(self, key, None) 
      elif key in ['Address1', 'Address2', 'Address3', 'Address4']: 
       setattr(self, key, value[:Property.MAXADDRESSLEN] if value else None) 
      elif key in ['LiableFrom','EmptySince']: 
       if type(value) == datetime.datetime: 
        setattr(self, key, value.date()) 
       elif type(value) == datetime.date: 
        setattr(self, key, value) 
       else: 
        setattr(self, key, None) 
      if key == 'UPRN': 
       if type(value) is str: 
        try: 
         setattr(self, key, int(value)) 
        except ValueError: 
         setattr(self, key, None) 
       elif type(value) is int: 
        setattr(self, key, value) 
       else: 
        setattr(self, key, None) 
      else: 
       setattr(self, key, value) 

UPDATE

。今すぐです

class Property(Base): 
    """ 
    Property details as imported from various Council sources 
    """ 
    MAXPROPREFLEN = 20 
    MAXADDRESSLEN = 80 
    MAXDESCRIPLEN = 80 
    MAXPOSTCODELEN = 10 

    __tablename__ = 'properties' 
    id    = Column(Integer, primary_key=True) 
    PropertyRef = Column(String(MAXPROPREFLEN)) # Council reference, diffrerent from UPRN 
    AccountHolder = Column(String(MAXDESCRIPLEN)) 
    Address1  = Column(String(MAXADDRESSLEN)) 
    Address2  = Column(String(MAXADDRESSLEN)) 
    Address3  = Column(String(MAXADDRESSLEN)) 
    Address4  = Column(String(MAXADDRESSLEN)) 
    PostCode  = Column(String(MAXPOSTCODELEN), index=True) 
    UPRN   = Column(BigInteger) 
    Description = Column(String(MAXDESCRIPLEN)) 
    RV    = Column(Numeric(10, 0)) 
    Empty   = Column(Boolean) 
    LiableFrom  = Column(Date) 
    EmptySince  = Column(Date) 
    MEBID   = Column(Integer) # Key in MEB table if applicable 
    Authority  = Column(Integer) # Key in authorities table 


    @validates('PropertyRef', 'AccountHolder', 'Description', 
       'Address1', 'Address2', 'Address3', 'Address4', 'PostCode') 
    def ValidateString(self, key, value): 
     maxlengths = {'PropertyRef': Property.MAXPROPREFLEN, 
         'AccountHolder': Property.MAXDESCRIPLEN, 
         'Description': Property.MAXDESCRIPLEN, 
         'Address1':  Property.MAXADDRESSLEN, 
         'Address2':  Property.MAXADDRESSLEN, 
         'Address3':  Property.MAXADDRESSLEN, 
         'Address4':  Property.MAXADDRESSLEN, 
         'PostCode':  Property.MAXPOSTCODELEN 
         } 

     if type(value) is str: 
      value = value.strip().upper() 
      if len(value) > maxlengths[key]: 
       logger.debug("Timmming {} <{}> to <{}> ({} to {} chars)".format(
          key, value, value[:maxlengths[key]], 
          len(value), maxlengths[key])) 
      return value[:maxlengths[key]] 
     else: 
      return None 

    @validates('LiableFrom', 'EmptySince') 
    def ValidateDate(self, key, value): 
     if type(value) == datetime.datetime: 
      return value.date() 
     elif type(value) == datetime.date: 
      return value 
     else: 
      return None 

    @validates('UPRN') 
    def ValidateInteger(self, key, value): 
     try: 
      return int(value) 
     except: 
      return None 

    @validates('RV') 
    def ValidateFloat(self, key, value): 
     try: 
      return float(value) 
     except: 
      return None 

あなたは簡単に知っていますか?

答えて

1

このようにしないでください。これにはコンセプトがあります - validatesdecoratorです。

属性バリデータは、属性の値を変異 のプロセスを停止、例外を発生させることができ、またはは異なる 何かに与えられた値を変更することができます。

変更された、フィルタされた、クリーンなデータのバリデーターに戻ります。

も参照してください。Changing Attribute Behaviorドキュメントのセクション。

関連する問題