Hi Mike,
In hindsight I might have responded prematurely - got around to trying it
and with text() I get the following:
__table_args__ = (
...
Index('folder_lower_name_idx', text('lower(name)'),
postgresql_ops={'name': 'text_pattern_ops'}),
)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 2798, in __init__
ColumnCollectionMixin.__init__(self, *columns)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 2231, in __init__
for c in columns]
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 2223, in _to_schema_column_or_string
raise exc.ArgumentError(msg % element)
ArgumentError: Element <sqlalchemy.sql.elements.TextClause object at
0x108e2b910> is not a string name or column element
With declared_attr:
@declared_attr
def __table_args__(cls):
return (
...
Index('folder_lower_name_idx', func.lower(cls.name),
postgresql_ops={'name': 'text_pattern_ops'}),
)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/flask_sqlalchemy.py",
line 477, in __init__
DeclarativeMeta.__init__(self, name, bases, d)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/ext/declarative/api.py",
line 53, in __init__
_as_declarative(cls, classname, cls.__dict__)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/ext/declarative/base.py",
line 251, in _as_declarative
**table_kw)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 352, in __new__
table._init(name, metadata, *args, **kw)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 429, in _init
self._init_items(*args)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 72, in _init_items
item._set_parent_with_dispatch(self)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/base.py",
line 421, in _set_parent_with_dispatch
self._set_parent(parent)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 2803, in _set_parent
ColumnCollectionMixin._set_parent(self, table)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/schema.py",
line 2241, in _set_parent
self.columns.add(col)
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/base.py",
line 490, in add
self[column.key] = column
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/base.py",
line 499, in __setitem__
if key in self:
File
"/Users/joshma/.envs/aurelia/lib/python2.7/site-packages/sqlalchemy/sql/base.py",
line 554, in __contains__
raise exc.ArgumentError("__contains__ requires a string argument")
ArgumentError: __contains__ requires a string argument
Is the functional index supported even if I'm using postgresql_ops? I've
re-installed and upgraded to SQLAlchemy 0.9.4, same errors.
- Josh
On Thu, Apr 17, 2014 at 4:57 PM, Joshua Ma <[email protected]> wrote:
> Awesome, thanks so much for the quick response.
>
>
> On Sun, Apr 13, 2014 at 7:00 PM, Michael Bayer
> <[email protected]>wrote:
>
>> you need to turn your __table_args__ into a callable:
>>
>> @declared_attr
>> def __table_args__(cls):
>> return (Index(…, func.lower(cls.name), …), )
>>
>> or just use a string for your functional index: Index(…,
>> text(“LOWER(name)”), …)
>>
>>
>> On Apr 13, 2014, at 9:22 PM, Joshua Ma <[email protected]> wrote:
>>
>> Is there a way to create a functional index in a declarative model
>> without referencing the actual column? I currently have something like
>>
>> class MyModel(db.Base):
>> name = db.Column('name', db.String(255))
>> __table_args__ = (
>> Index('mymodel_lower_name_idx', func.lower(name),
>> postgresql_ops={'name': 'text_pattern_ops'}),
>> )
>>
>> which is slightly inconvenient because I usually declare all my columns
>> under __table_args__.
>>
>> More importantly, though, I use a mixin for some models, with the
>> __table_args__ in the model and the column in the mixin:
>>
>> class MyMixin(object):
>> name = db.Column(db.String(64), nullable=False)
>>
>> class MyModel(MyMixin, db.Base):
>> __table_args__ = (
>> Index('mymodel_lower_name_idx', func.lower(MyMixin.name),
>> postgresql_ops={'name': 'text_pattern_ops'}),
>> )
>>
>> but this doesn't seem to work, I get "ArgumentError: __contains__
>> requires a string argument" at runtime.
>>
>> *The rest of my indices are just strings (e.g. Index('mymodel_name_idx',
>> 'name')) - is there a similar way to create functional ones?* I tried
>> 'lower(name)' but it doesn't like that either since it's not a valid column
>> (KeyError: 'lower(name)').
>>
>> Thanks!
>> Josh
>>
>> --
>> You received this message because you are subscribed to the Google Groups
>> "sqlalchemy" group.
>> To unsubscribe from this group and stop receiving emails from it, send an
>> email to [email protected].
>>
>> To post to this group, send email to [email protected].
>> Visit this group at http://groups.google.com/group/sqlalchemy.
>> For more options, visit https://groups.google.com/d/optout.
>>
>>
>> --
>> You received this message because you are subscribed to a topic in the
>> Google Groups "sqlalchemy" group.
>> To unsubscribe from this topic, visit
>> https://groups.google.com/d/topic/sqlalchemy/CgSJUlelhGs/unsubscribe.
>> To unsubscribe from this group and all its topics, send an email to
>> [email protected].
>> To post to this group, send email to [email protected].
>> Visit this group at http://groups.google.com/group/sqlalchemy.
>> For more options, visit https://groups.google.com/d/optout.
>>
>
>
--
You received this message because you are subscribed to the Google Groups
"sqlalchemy" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/sqlalchemy.
For more options, visit https://groups.google.com/d/optout.