одно поле с разными типами данных [SQLAlchemy] - PullRequest
1 голос
/ 02 июля 2010

У меня есть значение, которое может быть целым числом, числом с плавающей запятой или строкой, и я создал разные столбцы:

#declarative
class MyClass(Base):

    #id and other Columns
    _value_str = Column(String(100))
    _value_int = Column(Integer)
    _value_float = Column(Float)

    def __init__(self,...,value):
        self._value_str = value if isinstance(value,(str,unicode)) else None
        self._value_int = value if isinstance(value,int) else None
        self._value_float = value if isinstance(value,float) else None

и я хотел бы сделать что-то вроде этого:

>>> value = 'text'
>>> my_class = MyClass(value, ...)
>>> my_class.value
>>> 'text'
>>> session.add(my_class)
>>> session.commit()
#specialy this
>>> result = session.query(Myclass).filter(Myclass.value == 'text').one()
>>> print result.value 
>>> 'text'

Может быть, у меня проблема с дизайном, я согласен с любой хорошей идеей

Я новичок в SQLAlchemy

Спасибо

1 Ответ

2 голосов
/ 06 июля 2010

Вероятно, проблема дизайна - небольшое несоответствие между вашей БД и Python.В SQL переменные (столбцы) имеют тип, в то время как в значениях Python имеют тип.

Одной из возможностей может быть использование одного столбца (строки), но выбор значения перед сохранением.

Это может быть выполнено автоматически с помощью пользовательского типа sqlalchemy .

Что-то вроде следующего (для преобразования используется jsonpickle , а не cpickle):

import sqlalchemy.types as types
import jsonpickle
from copy import deepcopy

class JsonType(types.MutableType, types.TypeDecorator):    
    impl = types.Unicode

    def process_bind_param(self, value, engine):
        return unicode(jsonpickle.encode(value))

    def process_result_value(self, value, engine):
        if value:
            rv = jsonpickle.decode(value)
            return rv
        else:
            return None

    def copy_value(self, value):
        return deepcopy(value)

    def compare_values(self, x, y):
        return x == y

А затем используйте его следующим образом:

class MyClass(base):
    value = Column(JsonType())
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...