From: Mike Bayer Date: Wed, 19 Mar 2008 20:25:51 +0000 (+0000) Subject: added escape kw arg to contains(), startswith(), endswith(), [ticket:791] X-Git-Tag: rel_0_4_5~70 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=8d0c5672f06952382b4eedf78158a043b3529878;p=thirdparty%2Fsqlalchemy%2Fsqlalchemy.git added escape kw arg to contains(), startswith(), endswith(), [ticket:791] --- diff --git a/CHANGES b/CHANGES index ec08aef41d..d555062abd 100644 --- a/CHANGES +++ b/CHANGES @@ -44,10 +44,11 @@ CHANGES Column(). It (and .key) may now be deferred until the column is added to a Table. - - like() and ilike() take an optional keyword argument - "escape=", which is set as the escape character - using the syntax "x LIKE y ESCAPE ''" - [ticket:993] + - like(), ilike(), contains(), startswith(), endswith() + take an optional keyword argument "escape=", + which is set as the escape character using the syntax + "x LIKE y ESCAPE ''" [ticket:993], + [ticket:791] - extensions - The "synonym" function is now directly usable with diff --git a/lib/sqlalchemy/sql/expression.py b/lib/sqlalchemy/sql/expression.py index 701987e203..0d10c844ae 100644 --- a/lib/sqlalchemy/sql/expression.py +++ b/lib/sqlalchemy/sql/expression.py @@ -1146,14 +1146,14 @@ class ColumnOperators(Operators): def in_(self, *other): return self.operate(operators.in_op, other) - def startswith(self, other): - return self.operate(operators.startswith_op, other) + def startswith(self, other, **kwargs): + return self.operate(operators.startswith_op, other, **kwargs) - def endswith(self, other): - return self.operate(operators.endswith_op, other) + def endswith(self, other, **kwargs): + return self.operate(operators.endswith_op, other, **kwargs) - def contains(self, other): - return self.operate(operators.contains_op, other) + def contains(self, other, **kwargs): + return self.operate(operators.contains_op, other, **kwargs) def desc(self): return self.operate(operators.desc_op) @@ -1283,21 +1283,21 @@ class _CompareMixin(ColumnOperators): return self.__compare(op, ClauseList(*args).self_group(against=op), negate=negate_op) - def startswith(self, other): + def startswith(self, other, escape=None): """Produce the clause ``LIKE '%'``""" # use __radd__ to force string concat behavior - return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String).__radd__(self._check_literal(other))) + return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String).__radd__(self._check_literal(other)), escape=escape) - def endswith(self, other): + def endswith(self, other, escape=None): """Produce the clause ``LIKE '%'``""" - return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String) + self._check_literal(other)) + return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String) + self._check_literal(other), escape=escape) - def contains(self, other): + def contains(self, other, escape=None): """Produce the clause ``LIKE '%%'``""" - return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String) + self._check_literal(other) + literal_column("'%'", type_=sqltypes.String)) + return self.__compare(operators.like_op, literal_column("'%'", type_=sqltypes.String) + self._check_literal(other) + literal_column("'%'", type_=sqltypes.String), escape=escape) def label(self, name): """Produce a column label, i.e. `` AS ``. diff --git a/lib/sqlalchemy/sql/operators.py b/lib/sqlalchemy/sql/operators.py index 13f5e6131c..0047d1c732 100644 --- a/lib/sqlalchemy/sql/operators.py +++ b/lib/sqlalchemy/sql/operators.py @@ -49,14 +49,14 @@ def notin_op(a, b): def distinct_op(a): return a.distinct() -def startswith_op(a, b): - return a.startswith(b) +def startswith_op(a, b, escape=None): + return a.startswith(b, escape=escape) -def endswith_op(a, b): - return a.endswith(b) +def endswith_op(a, b, escape=None): + return a.endswith(b, escape=escape) -def contains_op(a, b): - return a.contains(b) +def contains_op(a, b, escape=None): + return a.contains(b, escape=escape) def comma_op(a, b): raise NotImplementedError() diff --git a/test/sql/select.py b/test/sql/select.py index 21b246d26e..24cff7702e 100644 --- a/test/sql/select.py +++ b/test/sql/select.py @@ -456,8 +456,11 @@ sq.myothertable_othername AS sq_myothertable_othername FROM (" + sqstring + ") A dialect=mysql.dialect() ) self.assert_compile( - table1.c.name.endswith('hn'), "mytable.name LIKE '%%' || :mytable_name_1", checkparams = {'mytable_name_1': u'hn'}, + table1.c.name.contains('jo', escape='\\'), "mytable.name LIKE '%%' || :mytable_name_1 || '%%' ESCAPE '\\'" , checkparams = {'mytable_name_1': u'jo'}, ) + self.assert_compile( table1.c.name.startswith('jo', escape='\\'), "mytable.name LIKE :mytable_name_1 || '%%' ESCAPE '\\'" ) + self.assert_compile( table1.c.name.endswith('jo', escape='\\'), "mytable.name LIKE '%%' || :mytable_name_1 ESCAPE '\\'" ) + self.assert_compile( table1.c.name.endswith('hn'), "mytable.name LIKE '%%' || :mytable_name_1", checkparams = {'mytable_name_1': u'hn'}, ) self.assert_compile( table1.c.name.endswith('hn'), "mytable.name LIKE concat('%%', %s)", checkparams = {'mytable_name_1': u'hn'}, dialect=mysql.dialect()