sqlobject-cvs Mailing List for SQLObject (Page 168)
SQLObject is a Python ORM.
Brought to you by:
ianbicking,
phd
You can subscribe to this list here.
2003 |
Jan
|
Feb
|
Mar
(9) |
Apr
(74) |
May
(29) |
Jun
(16) |
Jul
(28) |
Aug
(10) |
Sep
(57) |
Oct
(9) |
Nov
(29) |
Dec
(12) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2004 |
Jan
(7) |
Feb
(14) |
Mar
(6) |
Apr
(3) |
May
(12) |
Jun
(34) |
Jul
(9) |
Aug
(29) |
Sep
(22) |
Oct
(2) |
Nov
(15) |
Dec
(52) |
2005 |
Jan
(47) |
Feb
(78) |
Mar
(14) |
Apr
(35) |
May
(33) |
Jun
(16) |
Jul
(26) |
Aug
(63) |
Sep
(40) |
Oct
(96) |
Nov
(96) |
Dec
(123) |
2006 |
Jan
(159) |
Feb
(144) |
Mar
(64) |
Apr
(31) |
May
(88) |
Jun
(48) |
Jul
(16) |
Aug
(64) |
Sep
(87) |
Oct
(92) |
Nov
(56) |
Dec
(76) |
2007 |
Jan
(94) |
Feb
(103) |
Mar
(126) |
Apr
(123) |
May
(85) |
Jun
(11) |
Jul
(130) |
Aug
(47) |
Sep
(65) |
Oct
(70) |
Nov
(12) |
Dec
(11) |
2008 |
Jan
(30) |
Feb
(55) |
Mar
(88) |
Apr
(20) |
May
(50) |
Jun
|
Jul
(38) |
Aug
(1) |
Sep
(9) |
Oct
(5) |
Nov
(6) |
Dec
(39) |
2009 |
Jan
(8) |
Feb
(16) |
Mar
(3) |
Apr
(33) |
May
(44) |
Jun
(1) |
Jul
(10) |
Aug
(33) |
Sep
(74) |
Oct
(22) |
Nov
|
Dec
(15) |
2010 |
Jan
(28) |
Feb
(22) |
Mar
(46) |
Apr
(29) |
May
(1) |
Jun
(1) |
Jul
(27) |
Aug
(8) |
Sep
(5) |
Oct
(33) |
Nov
(24) |
Dec
(41) |
2011 |
Jan
(4) |
Feb
(12) |
Mar
(35) |
Apr
(29) |
May
(19) |
Jun
(16) |
Jul
(32) |
Aug
(25) |
Sep
(5) |
Oct
(11) |
Nov
(21) |
Dec
(12) |
2012 |
Jan
(3) |
Feb
(4) |
Mar
(20) |
Apr
(4) |
May
(25) |
Jun
(13) |
Jul
|
Aug
|
Sep
(2) |
Oct
(25) |
Nov
(9) |
Dec
(1) |
2013 |
Jan
(6) |
Feb
(8) |
Mar
|
Apr
(10) |
May
(31) |
Jun
(7) |
Jul
(18) |
Aug
(33) |
Sep
(4) |
Oct
(16) |
Nov
|
Dec
(27) |
2014 |
Jan
(2) |
Feb
|
Mar
|
Apr
(11) |
May
(39) |
Jun
(8) |
Jul
(11) |
Aug
(4) |
Sep
|
Oct
(27) |
Nov
|
Dec
(71) |
2015 |
Jan
(17) |
Feb
(47) |
Mar
(33) |
Apr
|
May
|
Jun
(9) |
Jul
(7) |
Aug
|
Sep
|
Oct
|
Nov
|
Dec
(8) |
2016 |
Jan
(4) |
Feb
(4) |
Mar
|
Apr
|
May
(12) |
Jun
(7) |
Jul
(9) |
Aug
(31) |
Sep
(8) |
Oct
(3) |
Nov
(15) |
Dec
(1) |
2017 |
Jan
(13) |
Feb
(7) |
Mar
(14) |
Apr
(8) |
May
(10) |
Jun
(4) |
Jul
(2) |
Aug
(1) |
Sep
|
Oct
(8) |
Nov
(4) |
Dec
(5) |
2018 |
Jan
(2) |
Feb
(8) |
Mar
|
Apr
(4) |
May
|
Jun
(6) |
Jul
|
Aug
(1) |
Sep
|
Oct
|
Nov
(1) |
Dec
|
2019 |
Jan
(1) |
Feb
(16) |
Mar
(1) |
Apr
(3) |
May
(5) |
Jun
(1) |
Jul
|
Aug
|
Sep
(2) |
Oct
|
Nov
(1) |
Dec
(3) |
2020 |
Jan
|
Feb
|
Mar
|
Apr
(1) |
May
(1) |
Jun
|
Jul
|
Aug
(1) |
Sep
|
Oct
(2) |
Nov
|
Dec
(2) |
2021 |
Jan
|
Feb
(2) |
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
(1) |
Nov
(1) |
Dec
|
2022 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
(6) |
Oct
(1) |
Nov
(1) |
Dec
(4) |
2023 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
(1) |
Aug
(3) |
Sep
(2) |
Oct
(2) |
Nov
(4) |
Dec
|
2024 |
Jan
|
Feb
(2) |
Mar
|
Apr
|
May
|
Jun
|
Jul
(1) |
Aug
|
Sep
(1) |
Oct
|
Nov
|
Dec
(9) |
2025 |
Jan
|
Feb
(4) |
Mar
(2) |
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
From: <sub...@co...> - 2005-03-01 18:04:53
|
Author: phd Date: 2005-03-01 18:04:32 +0000 (Tue, 01 Mar 2005) New Revision: 660 Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py Log: Fixed a bug in MySQLconnection - default port is indicated by 0, not ''. Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py =================================================================== --- trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-03-01 14:52:06 UTC (rev 659) +++ trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-03-01 18:04:32 UTC (rev 660) @@ -23,7 +23,7 @@ def connectionFromURI(cls, uri): user, password, host, port, path, args = cls._parseURI(uri) return cls(db=path.strip('/'), user=user or '', passwd=password or '', - host=host or 'localhost', port=port or '', **args) + host=host or 'localhost', port=port or 0, **args) connectionFromURI = classmethod(connectionFromURI) def makeConnection(self): |
From: <sub...@co...> - 2005-03-01 14:52:09
|
Author: phd Date: 2005-03-01 14:52:06 +0000 (Tue, 01 Mar 2005) New Revision: 659 Modified: trunk/SQLObject/docs/FAQ.txt trunk/SQLObject/docs/SQLObjectCustomization.txt trunk/SQLObject/docs/SQLObjectLegacy.txt trunk/SQLObject/docs/SQLObjectUse.txt Log: Fixed https://sourceforge.net/tracker/index.php?func=detail&aid=1072399&group_id=74338&atid=540672 - all mentions of .new() replaced with constructors. Modified: trunk/SQLObject/docs/FAQ.txt =================================================================== --- trunk/SQLObject/docs/FAQ.txt 2005-03-01 14:22:14 UTC (rev 658) +++ trunk/SQLObject/docs/FAQ.txt 2005-03-01 14:52:06 UTC (rev 659) @@ -159,7 +159,7 @@ ``CREATE TABLE`` generation (i.e., ``createTable``). You also will have to give your own ID values when creating an object, like:: - color = Something.new(id="blue", r=0, b=100, g=0) + color = Something(id="blue", r=0, b=100, g=0) IDs are, and always will in future versions, be considered immutable. Right now that is not enforced; you can assign to the ``id`` Modified: trunk/SQLObject/docs/SQLObjectCustomization.txt =================================================================== --- trunk/SQLObject/docs/SQLObjectCustomization.txt 2005-03-01 14:22:14 UTC (rev 658) +++ trunk/SQLObject/docs/SQLObjectCustomization.txt 2005-03-01 14:52:06 UTC (rev 659) @@ -41,8 +41,8 @@ keep in files as opposed to the database (such as large, opaque data like images). -You can also pass an ``image`` keyword argument to the `new` class -method or the `set` method, like ``Person.new(..., image=imageText)``. +You can also pass an ``image`` keyword argument to the constructor +or the `set` method, like ``Person(..., image=imageText)``. All of the methods (``_get_``, ``_set_``, etc) are optional -- you can use any one of them without using the others (except ``_doc_``, since Modified: trunk/SQLObject/docs/SQLObjectLegacy.txt =================================================================== --- trunk/SQLObject/docs/SQLObjectLegacy.txt 2005-03-01 14:22:14 UTC (rev 658) +++ trunk/SQLObject/docs/SQLObjectLegacy.txt 2005-03-01 14:52:06 UTC (rev 659) @@ -93,4 +93,4 @@ category of "irregularities". If you use non-integer keys, all primary key management is up to you. You must create the table yourself, and when you create instances you must pass a ``id`` keyword -argument into ``new`` (like ``Person.new(id='555-55-5555', ...)``). +argument into constructor (like ``Person(id='555-55-5555', ...)``). Modified: trunk/SQLObject/docs/SQLObjectUse.txt =================================================================== --- trunk/SQLObject/docs/SQLObjectUse.txt 2005-03-01 14:22:14 UTC (rev 658) +++ trunk/SQLObject/docs/SQLObjectUse.txt 2005-03-01 14:52:06 UTC (rev 659) @@ -16,7 +16,7 @@ method fetches a row. To create a new object (and row), use class instantiation. In this -case you might call ``Person.new(firstName="John", lastName="Doe")``. +case you might call ``Person(firstName="John", lastName="Doe")``. If you had left out ``firstName`` or ``lastName`` you would have gotten an error, as no default was given for these columns (``middleInitial`` has a default, so it will be set to ``NULL``, the |
From: <sub...@co...> - 2005-03-01 14:22:44
|
Author: phd Date: 2005-03-01 14:22:14 +0000 (Tue, 01 Mar 2005) New Revision: 658 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/tests/test_basic.py Log: Fixed bug https://sourceforge.net/tracker/index.php?func=detail&aid=1012150&group_id=74338&atid=540672. Foo.selectBy(column=None) now issues '... column IS NULL'. Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-03-01 13:04:43 UTC (rev 657) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-03-01 14:22:14 UTC (rev 658) @@ -478,10 +478,11 @@ self.sqlrepr(secondValue))) def _SO_columnClause(self, soClass, kw): + ops = {None: "IS"} return ' AND '.join( - ['%s = %s' % + ['%s %s %s' % (soClass.sqlmeta._columnDict[key].dbName, - self.sqlrepr(value)) + ops.get(value, "="), self.sqlrepr(value)) for key, value in kw.items()]) Modified: trunk/SQLObject/sqlobject/tests/test_basic.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_basic.py 2005-03-01 13:04:43 UTC (rev 657) +++ trunk/SQLObject/sqlobject/tests/test_basic.py 2005-03-01 14:22:14 UTC (rev 658) @@ -34,6 +34,7 @@ def test_count(): setupGetters(TestSO1) + assert TestSO1.selectBy(name=None).count() == 0 assert TestSO1.selectBy(name='bob').count() == 1 assert TestSO1.select(TestSO1.q.name == 'bob').count() == 1 assert TestSO1.select().count() == len(list(TestSO1.select())) |
From: <sub...@co...> - 2005-03-01 13:05:08
|
Author: phd Date: 2005-03-01 13:04:43 +0000 (Tue, 01 Mar 2005) New Revision: 657 Modified: trunk/SQLObject/sqlobject/sresults.py trunk/SQLObject/sqlobject/tests/test_minmax.py Log: accumulateMany() usage is now even simpler: select.accumulateMany(*atributes). Modified: trunk/SQLObject/sqlobject/sresults.py =================================================================== --- trunk/SQLObject/sqlobject/sresults.py 2005-03-01 09:40:03 UTC (rev 656) +++ trunk/SQLObject/sqlobject/sresults.py 2005-03-01 13:04:43 UTC (rev 657) @@ -1,6 +1,8 @@ import sqlbuilder import dbconnection +StringType = type('') + class SelectResults(object): IterationClass = dbconnection.Iteration @@ -147,41 +149,39 @@ count = min(self.ops['end'] - self.ops.get('start', 0), count) return count - def _accumulateOne(self, func_name, attribute): + def accumulateMany(self, *attributes): + """ Making the expressions for count/sum/min/max/avg + of a given select result attributes. + `attributes` must be a list/tuple of pairs (func_name, attribute); + `attribute` can be a column name (like 'a_column') + or a dot-q attribute (like Table.q.aColumn) + """ + expressions = [] + for func_name, attribute in attributes: + if type(attribute) == StringType: + expression = '%s(%s)' % (func_name, attribute) + else: + expression = getattr(sqlbuilder.func, func_name)(attribute) + expressions.append(expression) + return self.accumulate(*expressions) + + def accumulateOne(self, func_name, attribute): """ Making the sum/min/max/avg of a given select result attribute. `attribute` can be a column name (like 'a_column') or a dot-q attribute (like Table.q.aColumn) """ - return self.accumulate(*accumulateMany((func_name, attribute))) + return self.accumulateMany((func_name, attribute)) def sum(self, attribute): - return self._accumulateOne("SUM", attribute) + return self.accumulateOne("SUM", attribute) def min(self, attribute): - return self._accumulateOne("MIN", attribute) + return self.accumulateOne("MIN", attribute) def avg(self, attribute): - return self._accumulateOne("AVG", attribute) + return self.accumulateOne("AVG", attribute) def max(self, attribute): - return self._accumulateOne("MAX", attribute) + return self.accumulateOne("MAX", attribute) -StringType = type('') - -def accumulateMany(*attributes): - """ Making the expressions for sum/min/max/avg - of a given select result attributes. - `attributes` must be a list/tuple of pairs (func_name, attribute); - `attribute` can be a column name (like 'a_column') - or a dot-q attribute (like Table.q.aColumn) - """ - expressions = [] - for func_name, attribute in attributes: - if type(attribute) == StringType: - expression = '%s(%s)' % (func_name, attribute) - else: - expression = getattr(sqlbuilder.func, func_name)(attribute) - expressions.append(expression) - return expressions - -__all__ = ['SelectResults', 'accumulateMany'] +__all__ = ['SelectResults'] Modified: trunk/SQLObject/sqlobject/tests/test_minmax.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-03-01 09:40:03 UTC (rev 656) +++ trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-03-01 13:04:43 UTC (rev 657) @@ -1,5 +1,4 @@ from sqlobject import * -from sqlobject.sresults import * from sqlobject.tests.dbtest import * # Test MIN, AVG, MAX, SUM @@ -55,5 +54,6 @@ select = IntAccumulator.select() attribute = IntAccumulator.q.value - expression = accumulateMany(("MIN", attribute), ("AVG", attribute), ("MAX", attribute)) - assert select.accumulate(*expression) == (1, 2, 3) + assert select.accumulateMany( + ("MIN", attribute), ("AVG", attribute), ("MAX", attribute) + ) == (1, 2, 3) |
From: <sub...@co...> - 2005-03-01 09:40:24
|
Author: phd Date: 2005-03-01 09:40:03 +0000 (Tue, 01 Mar 2005) New Revision: 656 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/sresults.py trunk/SQLObject/sqlobject/tests/test_minmax.py Log: Changed the way accumalte functions work. Now you can accumulate a list of functions at once: select.accumulate(*accumulateMany(("MIN", attribute), ("MAX", attribute))). Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-03-01 09:35:22 UTC (rev 655) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-03-01 09:40:03 UTC (rev 656) @@ -264,14 +264,16 @@ return select.IterationClass(self, self.getConnection(), select, keepConnection=False) - def accumulateSelect(self, select, expression): - """ Apply an accumulate function (SUM, COUNT, MIN, AVG, MAX, etc...) + def accumulateSelect(self, select, *expressions): + """ Apply an accumulate function(s) (SUM, COUNT, MIN, AVG, MAX, etc...) to the select object. """ - q = "SELECT %s" % expression + q = "SELECT %s" % ", ".join([str(expression) for expression in expressions]) q += " FROM %s WHERE" % ", ".join(select.tables) q = self._addWhereClause(select, q, limit=0, order=0) - val = self.queryOne(q)[0] + val = self.queryOne(q) + if len(expressions) == 1: + val = val[0] return val def queryForSelect(self, select): Modified: trunk/SQLObject/sqlobject/sresults.py =================================================================== --- trunk/SQLObject/sqlobject/sresults.py 2005-03-01 09:35:22 UTC (rev 655) +++ trunk/SQLObject/sqlobject/sresults.py 2005-03-01 09:40:03 UTC (rev 656) @@ -127,14 +127,14 @@ conn = self.ops.get('connection', self.sourceClass._connection) return conn.iterSelect(self) - def accumulate(self, expression): - """ Use an accumulate expression to select result + def accumulate(self, *expressions): + """ Use accumulate expression(s) to select result using another SQL select through current connection. Return the accumulate result """ conn = self.ops.get('connection', self.sourceClass._connection) - return conn.accumulateSelect(self, expression) + return conn.accumulateSelect(self, *expressions) def count(self): """ Counting elements of current select results """ @@ -147,48 +147,41 @@ count = min(self.ops['end'] - self.ops.get('start', 0), count) return count - def sum(self, attribute): - """ Making the sum of a given select result attribute. + def _accumulateOne(self, func_name, attribute): + """ Making the sum/min/max/avg of a given select result attribute. `attribute` can be a column name (like 'a_column') or a dot-q attribute (like Table.q.aColumn) """ - if type(attribute) == type(''): - expression = 'SUM(%s)' % attribute - else: - expression = sqlbuilder.func.SUM(attribute) - return self.accumulate(expression) + return self.accumulate(*accumulateMany((func_name, attribute))) + def sum(self, attribute): + return self._accumulateOne("SUM", attribute) + def min(self, attribute): - """ Giving the min of a given select result attribute. - `attribute` can be a column name (like 'a_column') - or a dot-q attribute (like Table.q.aColumn) - """ - if type(attribute) == type(''): - expression = 'MIN(%s)' % attribute - else: - expression = sqlbuilder.func.MIN(attribute) - return self.accumulate(expression) + return self._accumulateOne("MIN", attribute) def avg(self, attribute): - """ Giving the average of a given select result attribute. - `attribute` can be a column name (like 'a_column') - or a dot-q attribute (like Table.q.aColumn) - """ - if type(attribute) == type(''): - expression = 'AVG(%s)' % attribute - else: - expression = sqlbuilder.func.AVG(attribute) - return self.accumulate(expression) + return self._accumulateOne("AVG", attribute) def max(self, attribute): - """ Giving the max of a given select result attribute. - `attribute` can be a column name (like 'a_column') - or a dot-q attribute (like Table.q.aColumn) - """ - if type(attribute) == type(''): - expression = 'MAX(%s)' % attribute + return self._accumulateOne("MAX", attribute) + +StringType = type('') + +def accumulateMany(*attributes): + """ Making the expressions for sum/min/max/avg + of a given select result attributes. + `attributes` must be a list/tuple of pairs (func_name, attribute); + `attribute` can be a column name (like 'a_column') + or a dot-q attribute (like Table.q.aColumn) + """ + expressions = [] + for func_name, attribute in attributes: + if type(attribute) == StringType: + expression = '%s(%s)' % (func_name, attribute) else: - expression = sqlbuilder.func.MAX(attribute) - return self.accumulate(expression) + expression = getattr(sqlbuilder.func, func_name)(attribute) + expressions.append(expression) + return expressions -__all__ = ['SelectResults'] +__all__ = ['SelectResults', 'accumulateMany'] Modified: trunk/SQLObject/sqlobject/tests/test_minmax.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-03-01 09:35:22 UTC (rev 655) +++ trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-03-01 09:40:03 UTC (rev 656) @@ -1,4 +1,5 @@ from sqlobject import * +from sqlobject.sresults import * from sqlobject.tests.dbtest import * # Test MIN, AVG, MAX, SUM @@ -44,3 +45,15 @@ assert floatcmp(FloatAccumulator.select().avg(FloatAccumulator.q.value), 2.5) == 0 assert floatcmp(FloatAccumulator.select().max(FloatAccumulator.q.value), 3.8) == 0 assert floatcmp(FloatAccumulator.select().sum(FloatAccumulator.q.value), 7.4) == 0 + + +def test_many(): + setupClass(IntAccumulator) + IntAccumulator(value=1) + IntAccumulator(value=2) + IntAccumulator(value=3) + + select = IntAccumulator.select() + attribute = IntAccumulator.q.value + expression = accumulateMany(("MIN", attribute), ("AVG", attribute), ("MAX", attribute)) + assert select.accumulate(*expression) == (1, 2, 3) |
From: <sub...@co...> - 2005-02-27 19:32:13
|
Author: phd Date: 2005-02-27 19:32:06 +0000 (Sun, 27 Feb 2005) New Revision: 652 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/tests/test_minmax.py Log: Some statistical functions (MIN, AVG, MAX) may return fload result. Added tests for float functions. Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-02-26 13:09:20 UTC (rev 651) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-02-27 19:32:06 UTC (rev 652) @@ -265,15 +265,13 @@ select, keepConnection=False) def accumulateSelect(self, select, expression): - """ Apply an accumulate function (like SUM, COUNT, ..) + """ Apply an accumulate function (SUM, COUNT, MIN, AVG, MAX, etc...) to the select object. - Return the value resulting from the SQL accumulate function - as an integer. """ q = "SELECT %s" % expression q += " FROM %s WHERE" % ", ".join(select.tables) q = self._addWhereClause(select, q, limit=0, order=0) - val = int(self.queryOne(q)[0]) + val = self.queryOne(q)[0] return val def queryForSelect(self, select): Modified: trunk/SQLObject/sqlobject/tests/test_minmax.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-02-26 13:09:20 UTC (rev 651) +++ trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-02-27 19:32:06 UTC (rev 652) @@ -3,19 +3,44 @@ # Test MIN, AVG, MAX, SUM -class Accumulator(SQLObject): + +class IntAccumulator(SQLObject): value = IntCol() -def test_minmax(): - setupClass(Accumulator) - Accumulator(value=1) - Accumulator(value=2) - Accumulator(value=3) - assert Accumulator.select().min(Accumulator.q.value) == 1 - assert Accumulator.select().avg(Accumulator.q.value) == 2 - assert Accumulator.select().max(Accumulator.q.value) == 3 - assert Accumulator.select().sum(Accumulator.q.value) == 6 +class FloatAccumulator(SQLObject): + value = FloatCol() - assert Accumulator.select(Accumulator.q.value > 1).max(Accumulator.q.value) == 3 - assert Accumulator.select(Accumulator.q.value > 1).sum(Accumulator.q.value) == 5 + +def test_integer(): + setupClass(IntAccumulator) + IntAccumulator(value=1) + IntAccumulator(value=2) + IntAccumulator(value=3) + + assert IntAccumulator.select().min(IntAccumulator.q.value) == 1 + assert IntAccumulator.select().avg(IntAccumulator.q.value) == 2 + assert IntAccumulator.select().max(IntAccumulator.q.value) == 3 + assert IntAccumulator.select().sum(IntAccumulator.q.value) == 6 + + assert IntAccumulator.select(IntAccumulator.q.value > 1).max(IntAccumulator.q.value) == 3 + assert IntAccumulator.select(IntAccumulator.q.value > 1).sum(IntAccumulator.q.value) == 5 + + +def floatcmp(f1, f2): + if abs(f1-f2) < 0.1: + return 0 + if f1 < f2: + return 1 + return -1 + +def test_float(): + setupClass(FloatAccumulator) + FloatAccumulator(value=1.2) + FloatAccumulator(value=2.4) + FloatAccumulator(value=3.8) + + assert floatcmp(FloatAccumulator.select().min(FloatAccumulator.q.value), 1.2) == 0 + assert floatcmp(FloatAccumulator.select().avg(FloatAccumulator.q.value), 2.5) == 0 + assert floatcmp(FloatAccumulator.select().max(FloatAccumulator.q.value), 3.8) == 0 + assert floatcmp(FloatAccumulator.select().sum(FloatAccumulator.q.value), 7.4) == 0 |
From: <sub...@co...> - 2005-02-26 13:09:27
|
Author: phd Date: 2005-02-26 13:09:20 +0000 (Sat, 26 Feb 2005) New Revision: 651 Modified: trunk/SQLObject/docs/Inheritance.txt trunk/SQLObject/sqlobject/inheritance/__init__.py trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py trunk/SQLObject/sqlobject/main.py Log: InheritableSQLObject are now inheritable by default - one does not need to set _inheritable = True. Tests and documentation were updated. Modified: trunk/SQLObject/docs/Inheritance.txt =================================================================== --- trunk/SQLObject/docs/Inheritance.txt 2005-02-25 17:50:40 UTC (rev 650) +++ trunk/SQLObject/docs/Inheritance.txt 2005-02-26 13:09:20 UTC (rev 651) @@ -21,13 +21,13 @@ The following code:: - class Person(SQLObject): - _inheritable = 1 # I want this class to be inherited + frim sqlobject.inheritance import InheritableSQLObject + class Person(InheritableSQLObject): firstName = StringCol() lastName = StringCol() class Employee(Person): - _inheritable = 0 # If I don't want this class to be inherited + _inheritable = False position = StringCol() will generate the following tables:: @@ -128,7 +128,7 @@ * You may not redefine columns in an inherited class (this will raise an exception). * If you don't want 'childName' columns in your last class (one that - will never be inherited), you must set '_inheritable' to 0 in this + will never be inherited), you must set '_inheritable' to False in this class. * I made it because I needed to be able to have automatic inheritance with linked table. @@ -138,4 +138,4 @@ * Thanks to Ian Bicking for SQLObject, this is a wonderful python module. * If you have suggestion, bugs, or patch to this patch, you can - contact me at <sqlobject xsoli.com> + contact SQLObject team: <sqlobject-discuss at lists.sourceforge.net> Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-25 17:50:40 UTC (rev 650) +++ trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-26 13:09:20 UTC (rev 651) @@ -65,6 +65,7 @@ class InheritableSQLObject(SQLObject): + _inheritable = True SelectResultsClass = InheritableSelectResults def get(cls, id, connection=None, selectResults=None, childResults=None, childUpdate=False): Modified: trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py 2005-02-25 17:50:40 UTC (rev 650) +++ trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py 2005-02-26 13:09:20 UTC (rev 651) @@ -8,12 +8,11 @@ class InherPerson(InheritableSQLObject): - _inheritable = 1 # I want this class to be inherited firstName = StringCol() lastName = StringCol(alternateID=True) class Employee(InherPerson): - _inheritable = 0 # If I don't want this class to be inherited + _inheritable = False position = StringCol() def setup(): Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-25 17:50:40 UTC (rev 650) +++ trunk/SQLObject/sqlobject/main.py 2005-02-26 13:09:20 UTC (rev 651) @@ -396,10 +396,11 @@ #DSM: inheritable class. If so, we keep a link to our parent class. cls._childClasses = {} for _cls in cls.__bases__: - if hasattr(_cls, '_inheritable') and _cls._inheritable: - cls._parentClass = _cls - cls._parent = None - _cls._childClasses[cls.__name__] = cls + if hasattr(_cls, '_inheritable') and _cls._inheritable and \ + _cls.__name__ <> "InheritableSQLObject": + cls._parentClass = _cls + cls._parent = None + _cls._childClasses[cls.__name__] = cls #DSM: If this class is a child of a parent class, we need to do some #DSM: attribute check and a a foreign key to the parent. @@ -421,9 +422,11 @@ cls._columns = [] #DSM: If this is inheritable, add some default columns # to be able to link to children - if hasattr(cls, '_inheritable') and cls._inheritable: - cls._columns.append( - col.StringCol(name='childName',default=None)) + if hasattr(cls, '_inheritable') and cls._inheritable and \ + cls.__name__ <> "InheritableSQLObject": + cls._columns.append( + col.StringCol(name='childName', default=None) + ) cls._columns.extend(implicitColumns) if not new_attrs.has_key('_joins'): |
From: <sub...@co...> - 2005-02-25 17:50:43
|
Author: phd Date: 2005-02-25 17:50:40 +0000 (Fri, 25 Feb 2005) New Revision: 650 Added: trunk/SQLObject/sqlobject/tests/test_minmax.py Modified: trunk/SQLObject/sqlobject/sresults.py Log: Added min() and max() - patch by michelts <mic...@gm...>. Added avg() and tests. Modified: trunk/SQLObject/sqlobject/sresults.py =================================================================== --- trunk/SQLObject/sqlobject/sresults.py 2005-02-25 15:37:35 UTC (rev 649) +++ trunk/SQLObject/sqlobject/sresults.py 2005-02-25 17:50:40 UTC (rev 650) @@ -158,4 +158,37 @@ expression = sqlbuilder.func.SUM(attribute) return self.accumulate(expression) + def min(self, attribute): + """ Giving the min of a given select result attribute. + `attribute` can be a column name (like 'a_column') + or a dot-q attribute (like Table.q.aColumn) + """ + if type(attribute) == type(''): + expression = 'MIN(%s)' % attribute + else: + expression = sqlbuilder.func.MIN(attribute) + return self.accumulate(expression) + + def avg(self, attribute): + """ Giving the average of a given select result attribute. + `attribute` can be a column name (like 'a_column') + or a dot-q attribute (like Table.q.aColumn) + """ + if type(attribute) == type(''): + expression = 'AVG(%s)' % attribute + else: + expression = sqlbuilder.func.AVG(attribute) + return self.accumulate(expression) + + def max(self, attribute): + """ Giving the max of a given select result attribute. + `attribute` can be a column name (like 'a_column') + or a dot-q attribute (like Table.q.aColumn) + """ + if type(attribute) == type(''): + expression = 'MAX(%s)' % attribute + else: + expression = sqlbuilder.func.MAX(attribute) + return self.accumulate(expression) + __all__ = ['SelectResults'] Added: trunk/SQLObject/sqlobject/tests/test_minmax.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-02-25 15:37:35 UTC (rev 649) +++ trunk/SQLObject/sqlobject/tests/test_minmax.py 2005-02-25 17:50:40 UTC (rev 650) @@ -0,0 +1,21 @@ +from sqlobject import * +from sqlobject.tests.dbtest import * + +# Test MIN, AVG, MAX, SUM + +class Accumulator(SQLObject): + value = IntCol() + +def test_minmax(): + setupClass(Accumulator) + Accumulator(value=1) + Accumulator(value=2) + Accumulator(value=3) + + assert Accumulator.select().min(Accumulator.q.value) == 1 + assert Accumulator.select().avg(Accumulator.q.value) == 2 + assert Accumulator.select().max(Accumulator.q.value) == 3 + assert Accumulator.select().sum(Accumulator.q.value) == 6 + + assert Accumulator.select(Accumulator.q.value > 1).max(Accumulator.q.value) == 3 + assert Accumulator.select(Accumulator.q.value > 1).sum(Accumulator.q.value) == 5 |
From: <sub...@co...> - 2005-02-25 15:37:39
|
Author: phd Date: 2005-02-25 15:37:35 +0000 (Fri, 25 Feb 2005) New Revision: 649 Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py Log: Fixed bugs with passing port to MySQLdb. Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py =================================================================== --- trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-25 15:19:35 UTC (rev 648) +++ trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-25 15:37:35 UTC (rev 649) @@ -8,12 +8,13 @@ dbName = 'mysql' schemes = [dbName] - def __init__(self, db, user, passwd='', host='localhost', **kw): + def __init__(self, db, user, passwd='', host='localhost', port=None, **kw): global MySQLdb if MySQLdb is None: import MySQLdb self.module = MySQLdb self.host = host + self.port = port self.db = db self.user = user self.password = passwd @@ -26,7 +27,7 @@ connectionFromURI = classmethod(connectionFromURI) def makeConnection(self): - return MySQLdb.connect(host=self.host, db=self.db, + return MySQLdb.connect(host=self.host, port=self.port, db=self.db, user=self.user, passwd=self.password) def _executeRetry(self, conn, cursor, query): |
From: <sub...@co...> - 2005-02-25 15:19:44
|
Author: phd Date: 2005-02-25 15:19:35 +0000 (Fri, 25 Feb 2005) New Revision: 648 Modified: trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py Log: Fixed a bug with autocommit in sqlite. Modified: trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py =================================================================== --- trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-24 22:56:21 UTC (rev 647) +++ trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-25 15:19:35 UTC (rev 648) @@ -18,7 +18,7 @@ kw['pool'] = 0 # use only one connection for sqlite - supports multiple # cursors per connection - self._conn = sqlite.connect(self.filename) + self._conn = sqlite.connect(self.filename, autocommit=autoCommit) DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): |
From: <sub...@co...> - 2005-02-24 22:56:49
|
Author: phd Date: 2005-02-24 22:56:21 +0000 (Thu, 24 Feb 2005) New Revision: 647 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/tests/test_parse.py Log: _parseURI() now translate paths from C|/path to C:/path on w32 platforms. Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-02-24 14:05:57 UTC (rev 646) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-02-24 22:56:21 UTC (rev 647) @@ -105,6 +105,9 @@ else: port = None path = '/' + rest + if os.name == 'nt': + if (len(rest) > 1) and (rest[1] == '|'): + path = "%s:%s" % (rest[0], rest[2:]) args = {} if path.find('?') != -1: path, arglist = path.split('?', 1) Modified: trunk/SQLObject/sqlobject/tests/test_parse.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-24 14:05:57 UTC (rev 646) +++ trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-24 22:56:21 UTC (rev 647) @@ -1,3 +1,4 @@ +import os from sqlobject.dbconnection import DBConnection ######################################## @@ -54,3 +55,12 @@ assert port is None assert path == "/:memory:" assert args == {} + + if os.name == 'nt': + user, password, host, port, path, args = _parseURI("sqlite:/C|/full/path/to/database") + assert user is None + assert password is None + assert host is None + assert port is None + assert path == "C:/full/path/to/database" + assert args == {} |
From: <sub...@co...> - 2005-02-24 14:06:22
|
Author: phd Date: 2005-02-24 14:05:57 +0000 (Thu, 24 Feb 2005) New Revision: 646 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/firebird/firebirdconnection.py trunk/SQLObject/sqlobject/maxdb/maxdbconnection.py trunk/SQLObject/sqlobject/mysql/mysqlconnection.py trunk/SQLObject/sqlobject/postgres/pgconnection.py trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py trunk/SQLObject/sqlobject/sybase/sybaseconnection.py trunk/SQLObject/sqlobject/tests/test_parse.py Log: _parseURI now splits host and port, if the host contains :port. Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -93,6 +93,17 @@ password = None else: user = password = None + if host and host.find(':') != -1: + _host, port = host.split(':') + try: + port = int(port) + except ValueError: + raise ValueError, "port must be integer, got '%s' instead" % port + if not (1 <= port <= 65535): + raise ValueError, "port must be integer in the range 1-65535, got '%d' instead" % port + host = _host + else: + port = None path = '/' + rest args = {} if path.find('?') != -1: @@ -102,7 +113,7 @@ argname, argvalue = single.split('=', 1) argvalue = urllib.unquote(argvalue) args[argname] = argvalue - return user, password, host, path, args + return user, password, host, port, path, args _parseURI = staticmethod(_parseURI) class DBAPI(DBConnection): Modified: trunk/SQLObject/sqlobject/firebird/firebirdconnection.py =================================================================== --- trunk/SQLObject/sqlobject/firebird/firebirdconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/firebird/firebirdconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -16,7 +16,7 @@ if kinterbasdb is None: import kinterbasdb self.module = kinterbasdb - + self.limit_re = re.compile('^\s*(select )(.*)', re.IGNORECASE) if not autoCommit and not kw.has_key('pool'): @@ -37,7 +37,7 @@ DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): - auth, password, host, path, args = cls._parseURI(uri) + auth, password, host, port, path, args = cls._parseURI(uri) if not password: password = 'masterkey' if not auth: @@ -45,7 +45,7 @@ path = path.replace('/', os.sep) return cls(host, db=path, user=auth, passwd=password, **args) connectionFromURI = classmethod(connectionFromURI) - + def _runWithConnection(self, meth, *args): conn = self.getConnection() # @@: Horrible auto-commit implementation. Just horrible! Modified: trunk/SQLObject/sqlobject/maxdb/maxdbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/maxdb/maxdbconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/maxdb/maxdbconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -78,7 +78,7 @@ DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): - auth, password, host, path, args = cls._parseURI(uri) + auth, password, host, port, path, args = cls._parseURI(uri) path = path.replace('/', os.path.sep) return cls(host, db=path, user=auth, passwd=password, **args) connectionFromURI = classmethod(connectionFromURI) Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py =================================================================== --- trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -20,9 +20,9 @@ DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): - user, password, host, path, args = cls._parseURI(uri) + user, password, host, port, path, args = cls._parseURI(uri) return cls(db=path.strip('/'), user=user or '', passwd=password or '', - host=host or 'localhost', **args) + host=host or 'localhost', port=port or '', **args) connectionFromURI = classmethod(connectionFromURI) def makeConnection(self): Modified: trunk/SQLObject/sqlobject/postgres/pgconnection.py =================================================================== --- trunk/SQLObject/sqlobject/postgres/pgconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/postgres/pgconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -12,7 +12,7 @@ dbName = 'postgres' schemes = [dbName, 'postgresql', 'psycopg'] - def __init__(self, dsn=None, host=None, db=None, + def __init__(self, dsn=None, host=None, port=None, db=None, user=None, passwd=None, usePygresql=False, **kw): global psycopg, pgdb @@ -31,6 +31,7 @@ self.user = user self.host = host + self.port = port self.db = db self.password = passwd if dsn is None: @@ -44,6 +45,8 @@ if host: # @@: right format? dsn.append('host=%s' % host) + if port: + dsn.append('port=%s' % port) dsn = ' '.join(dsn) self.dsn = dsn DBAPI.__init__(self, **kw) @@ -52,9 +55,9 @@ self._server_version = None # Not yet initialized def connectionFromURI(cls, uri): - user, password, host, path, args = cls._parseURI(uri) + user, password, host, port, path, args = cls._parseURI(uri) path = path.strip('/') - return cls(host=host, db=path, user=user, passwd=password, **args) + return cls(host=host, port=port, db=path, user=user, passwd=password, **args) connectionFromURI = classmethod(connectionFromURI) def _setAutoCommit(self, conn, auto): Modified: trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py =================================================================== --- trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -22,7 +22,7 @@ DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): - user, password, host, path, args = cls._parseURI(uri) + user, password, host, port, path, args = cls._parseURI(uri) assert host is None, ( "SQLite can only be used locally (with a URI like " "sqlite:///file or sqlite:/file, not %r)" % uri) Modified: trunk/SQLObject/sqlobject/sybase/sybaseconnection.py =================================================================== --- trunk/SQLObject/sqlobject/sybase/sybaseconnection.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/sybase/sybaseconnection.py 2005-02-24 14:05:57 UTC (rev 646) @@ -33,7 +33,7 @@ DBAPI.__init__(self, **kw) def connectionFromURI(cls, uri): - user, password, host, path, args = cls._parseURI(uri) + user, password, host, port, path, args = cls._parseURI(uri) return cls(user=user, passwd=password, host=host or 'localhost', db=path, **args) connectionFromURI = classmethod(connectionFromURI) Modified: trunk/SQLObject/sqlobject/tests/test_parse.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-24 04:18:55 UTC (rev 645) +++ trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-24 14:05:57 UTC (rev 646) @@ -7,44 +7,50 @@ def test_parse(): _parseURI = DBConnection._parseURI - user, password, host, path, args = _parseURI("mysql://user:passwd@host/database") + user, password, host, port, path, args = _parseURI("mysql://user:passwd@host/database") assert user == "user" assert password == "passwd" assert host == "host" + assert port is None assert path == "/database" assert args == {} - user, password, host, path, args = _parseURI("mysql://host/database") - assert user == None - assert password == None + user, password, host, port, path, args = _parseURI("mysql://host/database") + assert user is None + assert password is None assert host == "host" + assert port is None assert path == "/database" assert args == {} - user, password, host, path, args = _parseURI("postgres://user@host/database") + user, password, host, port, path, args = _parseURI("postgres://user@host/database") assert user == "user" - assert password == None + assert password is None assert host == "host" + assert port is None assert path == "/database" assert args == {} - user, password, host, path, args = _parseURI("postgres://host:5432/database") - assert user == None - assert password == None - assert host == "host:5432" + user, password, host, port, path, args = _parseURI("postgres://host:5432/database") + assert user is None + assert password is None + assert host == "host" + assert port == 5432 assert path == "/database" assert args == {} - user, password, host, path, args = _parseURI("sqlite:///full/path/to/database") - assert user == None - assert password == None - assert host == None + user, password, host, port, path, args = _parseURI("sqlite:///full/path/to/database") + assert user is None + assert password is None + assert host is None + assert port is None assert path == "/full/path/to/database" assert args == {} - user, password, host, path, args = _parseURI("sqlite:/:memory:") - assert user == None - assert password == None - assert host == None + user, password, host, port, path, args = _parseURI("sqlite:/:memory:") + assert user is None + assert password is None + assert host is None + assert port is None assert path == "/:memory:" assert args == {} |
From: <sub...@co...> - 2005-02-23 19:28:33
|
Author: phd Date: 2005-02-23 19:28:17 +0000 (Wed, 23 Feb 2005) New Revision: 638 Modified: trunk/SQLObject/sqlobject/cache.py trunk/SQLObject/sqlobject/inheritance/__init__.py trunk/SQLObject/sqlobject/main.py Log: The patch simplified and made faster inherited _SO_fetchAlternateID (_findAlternateID, actually), but changed their signatures. Fixed a minor bug in cache.py expireAll(). Modified: trunk/SQLObject/sqlobject/cache.py =================================================================== --- trunk/SQLObject/sqlobject/cache.py 2005-02-23 19:19:42 UTC (rev 637) +++ trunk/SQLObject/sqlobject/cache.py 2005-02-23 19:28:17 UTC (rev 638) @@ -225,7 +225,7 @@ self.lock.acquire() try: for key, value in self.cache.items(): - self.expiredCache[key] = ref(obj) + self.expiredCache[key] = ref(value) self.cache = {} finally: self.lock.release() Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-23 19:19:42 UTC (rev 637) +++ trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-23 19:28:17 UTC (rev 638) @@ -193,21 +193,8 @@ super(InheritableSQLObject, self)._create(id, **kw) - def _findAlternateID(cls, dbIDName, value, connection=None): - found = False - currentClass = cls - try: - while currentClass: - for col in currentClass.sqlmeta._columns: - if col.dbName == dbIDName: - found = True - raise StopIteration - currentClass = currentClass._parentClass - except StopIteration: - pass - if not found: - return [], None - result = list(cls.selectBy(connection, **{col.name: value})) + def _findAlternateID(cls, name, dbName, value, connection=None): + result = list(cls.selectBy(connection, **{name: value})) if not result: return result, None obj = result[0] Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-23 19:19:42 UTC (rev 637) +++ trunk/SQLObject/sqlobject/main.py 2005-02-23 19:28:17 UTC (rev 638) @@ -649,7 +649,7 @@ cls, '_SO_class_%s' % column.foreignKey) if column.alternateMethodName: - func = eval('lambda cls, val, connection=None: cls._SO_fetchAlternateID(%s, val, connection=connection)' % repr(column.dbName)) + func = eval('lambda cls, val, connection=None: cls._SO_fetchAlternateID(%s, %s, val, connection=connection)' % (repr(column.name), repr(column.dbName))) setattr(cls, column.alternateMethodName, classmethod(func)) if changeSchema: @@ -1119,19 +1119,19 @@ def _SO_getID(self, obj): return getID(obj) - def _findAlternateID(cls, dbIDName, value, connection=None): + def _findAlternateID(cls, name, dbName, value, connection=None): return (connection or cls._connection)._SO_selectOneAlt( cls, [cls.sqlmeta.idName] + [col.dbName for col in cls.sqlmeta._columns], - dbIDName, + dbName, value), None _findAlternateID = classmethod(_findAlternateID) - def _SO_fetchAlternateID(cls, dbIDName, value, connection=None): - result, obj = cls._findAlternateID(dbIDName, value, connection) + def _SO_fetchAlternateID(cls, name, dbName, value, connection=None): + result, obj = cls._findAlternateID(name, dbName, value, connection) if not result: - raise SQLObjectNotFound, "The %s by alternateID %s=%s does not exist" % (cls.__name__, dbIDName, repr(value)) + raise SQLObjectNotFound, "The %s by alternateID %s=%s does not exist" % (cls.__name__, name, repr(value)) if obj: return obj if connection: |
From: <sub...@co...> - 2005-02-22 12:32:45
|
Author: phd Date: 2005-02-22 12:32:34 +0000 (Tue, 22 Feb 2005) New Revision: 635 Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py trunk/SQLObject/sqlobject/main.py Log: Fixed bugs in nherited byAlternateID() and selectBy(). Split _SO_fetchAlternateID() into _findAlternateID() overrided _findAlternateID() in InheritableSQLObject. Added more inheritance tests. Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-21 16:50:34 UTC (rev 634) +++ trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-22 12:32:34 UTC (rev 635) @@ -193,6 +193,37 @@ super(InheritableSQLObject, self)._create(id, **kw) + def _findAlternateID(cls, dbIDName, value, connection=None): + found = False + currentClass = cls + try: + while currentClass: + for col in currentClass.sqlmeta._columns: + if col.dbName == dbIDName: + found = True + raise StopIteration + currentClass = currentClass._parentClass + except StopIteration: + pass + if not found: + return [], None + result = list(cls.selectBy(connection, **{col.name: value})) + if not result: + return result, None + obj = result[0] + return [obj.id], obj + _findAlternateID = classmethod(_findAlternateID) + + def selectBy(cls, connection=None, **kw): + clause = [] + for name, value in kw.items(): + clause.append(getattr(cls.q, name) == value) + clause = reduce(sqlbuilder.AND, clause) + conn = connection or cls._connection + return cls.SelectResultsClass(cls, clause, connection=conn) + + selectBy = classmethod(selectBy) + def destroySelf(self): #DSM: If this object has parents, recursivly kill them if hasattr(self, '_parent') and self._parent: Modified: trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py 2005-02-21 16:50:34 UTC (rev 634) +++ trunk/SQLObject/sqlobject/inheritance/tests/test_inheritance.py 2005-02-22 12:32:34 UTC (rev 635) @@ -10,7 +10,7 @@ class InherPerson(InheritableSQLObject): _inheritable = 1 # I want this class to be inherited firstName = StringCol() - lastName = StringCol() + lastName = StringCol(alternateID=True) class Employee(InherPerson): _inheritable = 0 # If I don't want this class to be inherited @@ -20,8 +20,8 @@ setupClass(InherPerson) setupClass(Employee) - Employee(firstName='Ian', lastName='Bicking', position='Project leader') - InherPerson(firstName='Daniel', lastName='Savard') + Employee(firstName='Project', lastName='Leader', position='Project leader') + InherPerson(firstName='Oneof', lastName='Authors') def test_inheritance(): @@ -43,8 +43,34 @@ persons = InherPerson.select(InherPerson.q.firstName <> None) assert persons.count() == 2 + persons = InherPerson.select(InherPerson.q.firstName == "phd") + assert persons.count() == 0 + employees = Employee.select(Employee.q.firstName <> None) assert employees.count() == 1 + employees = Employee.select(Employee.q.firstName == "phd") + assert employees.count() == 0 + employees = Employee.select(Employee.q.position <> None) assert employees.count() == 1 + + persons = InherPerson.selectBy(firstName="Project") + assert persons.count() == 1 + assert isinstance(persons[0], Employee) + + persons = Employee.selectBy(firstName="Project") + assert persons.count() == 1 + + try: + person = InherPerson.byLastName("Oneof") + except: + pass + else: + raise RuntimeError, "unknown person %s" % person + + person = InherPerson.byLastName("Leader") + assert person.firstName == "Project" + + person = Employee.byLastName("Leader") + assert person.firstName == "Project" Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-21 16:50:34 UTC (rev 634) +++ trunk/SQLObject/sqlobject/main.py 2005-02-22 12:32:34 UTC (rev 635) @@ -1119,15 +1119,21 @@ def _SO_getID(self, obj): return getID(obj) - def _SO_fetchAlternateID(cls, dbIDName, value, connection=None): - result = (connection or cls._connection)._SO_selectOneAlt( + def _findAlternateID(cls, dbIDName, value, connection=None): + return (connection or cls._connection)._SO_selectOneAlt( cls, [cls.sqlmeta.idName] + [col.dbName for col in cls.sqlmeta._columns], dbIDName, - value) + value), None + _findAlternateID = classmethod(_findAlternateID) + + def _SO_fetchAlternateID(cls, dbIDName, value, connection=None): + result, obj = cls._findAlternateID(dbIDName, value, connection) if not result: raise SQLObjectNotFound, "The %s by alternateID %s=%s does not exist" % (cls.__name__, dbIDName, repr(value)) + if obj: + return obj if connection: obj = cls.get(result[0], connection=connection) else: |
From: <sub...@co...> - 2005-02-21 16:50:39
|
Author: phd Date: 2005-02-21 16:50:34 +0000 (Mon, 21 Feb 2005) New Revision: 634 Added: trunk/SQLObject/sqlobject/tests/test_parse.py Modified: trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py Log: Fixed a bug in sqlite connection - allow in-memory database with sqlite:/:memory: URI. Added tests for _parseURI. Modified: trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py =================================================================== --- trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-21 13:39:55 UTC (rev 633) +++ trunk/SQLObject/sqlobject/sqlite/sqliteconnection.py 2005-02-21 16:50:34 UTC (rev 634) @@ -29,6 +29,7 @@ assert user is None and password is None, ( "You may not provide usernames or passwords for SQLite " "databases") + if path == "/:memory:": path = ":memory:" return cls(filename=path, **args) connectionFromURI = classmethod(connectionFromURI) Added: trunk/SQLObject/sqlobject/tests/test_parse.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-21 13:39:55 UTC (rev 633) +++ trunk/SQLObject/sqlobject/tests/test_parse.py 2005-02-21 16:50:34 UTC (rev 634) @@ -0,0 +1,50 @@ +from sqlobject.dbconnection import DBConnection + +######################################## +## Test _parseURI +######################################## + +def test_parse(): + _parseURI = DBConnection._parseURI + + user, password, host, path, args = _parseURI("mysql://user:passwd@host/database") + assert user == "user" + assert password == "passwd" + assert host == "host" + assert path == "/database" + assert args == {} + + user, password, host, path, args = _parseURI("mysql://host/database") + assert user == None + assert password == None + assert host == "host" + assert path == "/database" + assert args == {} + + user, password, host, path, args = _parseURI("postgres://user@host/database") + assert user == "user" + assert password == None + assert host == "host" + assert path == "/database" + assert args == {} + + user, password, host, path, args = _parseURI("postgres://host:5432/database") + assert user == None + assert password == None + assert host == "host:5432" + assert path == "/database" + assert args == {} + + user, password, host, path, args = _parseURI("sqlite:///full/path/to/database") + assert user == None + assert password == None + assert host == None + assert path == "/full/path/to/database" + assert args == {} + + user, password, host, path, args = _parseURI("sqlite:/:memory:") + assert user == None + assert password == None + assert host == None + assert path == "/:memory:" + assert args == {} |
From: <sub...@co...> - 2005-02-21 13:39:58
|
Author: phd Date: 2005-02-21 13:39:55 +0000 (Mon, 21 Feb 2005) New Revision: 633 Removed: home/phd/SQLObject/inheritance/ home/phd/SQLObject/postgres-7.2/ Log: Removed old private branches. Inheritance has been merged into the trunk, and Postgres 7.2 is just too old to be merged. |
From: <sub...@co...> - 2005-02-21 13:37:13
|
Author: phd Date: 2005-02-21 13:37:09 +0000 (Mon, 21 Feb 2005) New Revision: 632 Modified: trunk/SQLObject/docs/News.txt Log: Started new section about SQLObject 0.7.0. Modified: trunk/SQLObject/docs/News.txt =================================================================== --- trunk/SQLObject/docs/News.txt 2005-02-21 13:33:48 UTC (rev 631) +++ trunk/SQLObject/docs/News.txt 2005-02-21 13:37:09 UTC (rev 632) @@ -7,6 +7,17 @@ .. _start: +SQLObject 0.7.0 +=============== + +Features +-------- + +* Inheritance. See Inheritance.html_ + +.. _Inheritance.html: Inheritance.html + + SQLObject 0.6.1 =============== |
From: <sub...@co...> - 2005-02-21 13:33:53
|
Author: phd Date: 2005-02-21 13:33:48 +0000 (Mon, 21 Feb 2005) New Revision: 631 Modified: trunk/SQLObject/docs/Inheritance.txt trunk/SQLObject/docs/build Log: Minor inheritance documentation update. Modified: trunk/SQLObject/docs/Inheritance.txt =================================================================== --- trunk/SQLObject/docs/Inheritance.txt 2005-02-21 12:49:20 UTC (rev 630) +++ trunk/SQLObject/docs/Inheritance.txt 2005-02-21 13:33:48 UTC (rev 631) @@ -3,6 +3,13 @@ Inheritance ----------- +Daniel Savard has implemented inheritance for SQLObject. According to +ObjectMatter_ this is a kind of vertical inheritance. The only difference +is that objects reference their leafs, not parents. Links to parents are +reconstructed at run-time using the hierarchy of Python classes. + +.. _ObjectMatter: http://www.objectmatter.com/vbsf/docs/maptool/ormapping.html + * As suggested by Ian Bicking, each child class now has the same ID than the parent class. No more need for childID column and parent foreignKey (with a small speed boost). Modified: trunk/SQLObject/docs/build =================================================================== --- trunk/SQLObject/docs/build 2005-02-21 12:49:20 UTC (rev 630) +++ trunk/SQLObject/docs/build 2005-02-21 13:33:48 UTC (rev 631) @@ -1,7 +1,6 @@ #!/bin/sh -cd ../examples -./examplestripper.py -cd ../docs -buildhtml.py --report=2 --prune=.svn --prune=europython --silent --no-toc-backlinks - +cd ../examples && \ +./examplestripper.py && \ +cd ../docs && \ +exec buildhtml.py --report=2 --prune=.svn --prune=europython --silent --no-toc-backlinks |
From: <sub...@co...> - 2005-02-21 12:49:27
|
Author: phd Date: 2005-02-21 12:49:20 +0000 (Mon, 21 Feb 2005) New Revision: 630 Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py Log: Applied the patch from https://sourceforge.net/tracker/index.php?func=detail&aid=1040262&group_id=74338&atid=540672 Modified: trunk/SQLObject/sqlobject/mysql/mysqlconnection.py =================================================================== --- trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-21 12:43:02 UTC (rev 629) +++ trunk/SQLObject/sqlobject/mysql/mysqlconnection.py 2005-02-21 12:49:20 UTC (rev 630) @@ -52,7 +52,10 @@ self.printDebug(conn, q, 'QueryIns') self._executeRetry(conn, c, q) if id is None: - id = c.lastrowid + try: + id = c.lastrowid + except AttributeError: + id = c.insert_id() if self.debugOutput: self.printDebug(conn, id, 'QueryIns', 'result') return id |
From: <sub...@co...> - 2005-02-21 12:43:08
|
Author: phd Date: 2005-02-21 12:43:02 +0000 (Mon, 21 Feb 2005) New Revision: 629 Modified: trunk/SQLObject/sqlobject/sybase/sybaseconnection.py Log: Applied the patch from https://sourceforge.net/tracker/index.php?func=detail&aid=1104058&group_id=74338&atid=540674 Modified: trunk/SQLObject/sqlobject/sybase/sybaseconnection.py =================================================================== --- trunk/SQLObject/sqlobject/sybase/sybaseconnection.py 2005-02-21 12:32:50 UTC (rev 628) +++ trunk/SQLObject/sqlobject/sybase/sybaseconnection.py 2005-02-21 12:43:02 UTC (rev 629) @@ -1,4 +1,5 @@ from sqlobject.dbconnection import DBAPI +from sqlobject import col Sybase = None class SybaseConnection(DBAPI): @@ -128,13 +129,13 @@ (tableName, column.dbName)) - SHOW_COLUMNS=("select 'column' = COL_NAME(id, colid) " - "from syscolumns where id = OBJECT_ID(%s)") + SHOW_COLUMNS=('SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE, COLUMN_DEFAULT FROM INFORMATION_SCHEMA.COLUMNS ' + 'WHERE TABLE_NAME = \'%s\'') def columnsFromSchema(self, tableName, soClass): colData = self.queryAll(self.SHOW_COLUMNS % tableName) results = [] - for field, t, nullAllowed, key, default, extra in colData: + for field, t, nullAllowed, default in colData: if field == 'id': continue colClass, kw = self.guessClass(t) @@ -143,6 +144,7 @@ kw['default'] = default # @@ skip key... # @@ skip extra... + kw['forceDBName'] = True results.append(colClass(**kw)) return results |
From: <sub...@co...> - 2005-02-21 12:32:59
|
Author: phd Date: 2005-02-21 12:32:50 +0000 (Mon, 21 Feb 2005) New Revision: 628 Modified: trunk/SQLObject/sqlobject/main.py Log: Minor code cleanup - removed trailing spaces. Added connection parameter to method .delete(). Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-20 09:33:10 UTC (rev 627) +++ trunk/SQLObject/sqlobject/main.py 2005-02-21 12:32:50 UTC (rev 628) @@ -337,9 +337,9 @@ # Magic values shouldn't be passed through: del values[key] cls.sqlmeta = type('sqlmeta', (superclass,), values) - + cls.sqlmeta.setClass(cls) - + implicitColumns = [] implicitJoins = [] implicitIndexes = [] @@ -358,7 +358,7 @@ value.setName(attr) implicitIndexes.append(value) delattr(cls, attr) - continue + continue if not is_base: cls._cleanDeprecatedAttrs(new_attrs) @@ -516,7 +516,7 @@ def get(cls, id, connection=None, selectResults=None): assert id is not None, 'None is not a possible id for %s' % cls.__name - + id = cls._idType(id) if connection is None: @@ -1291,8 +1291,8 @@ self._connection._SO_delete(self) self._connection.cache.expire(self.id, self.__class__) - def delete(cls, id): - obj = cls.get(id) + def delete(cls, id, connection=None): + obj = cls.get(id, connection=connection) obj.destroySelf() delete = classmethod(delete) |
From: <sub...@co...> - 2005-02-20 09:33:18
|
Author: ianb Date: 2005-02-20 09:33:10 +0000 (Sun, 20 Feb 2005) New Revision: 627 Modified: trunk/SQLObject/sqlobject/dbconnection.py trunk/SQLObject/sqlobject/index.py trunk/SQLObject/sqlobject/inheritance/iteration.py trunk/SQLObject/sqlobject/main.py trunk/SQLObject/sqlobject/sqlbuilder.py trunk/SQLObject/sqlobject/sresults.py trunk/SQLObject/sqlobject/tests/test_basic.py trunk/SQLObject/sqlobject/tests/test_style.py trunk/SQLObject/sqlobject/tests/test_style_old.py Log: Moved more attributes into sqlmeta, including attributes that are per-class and private (like _SO_columns); these get set in sqlmeta.setClass Added a test for .set() usage (apparently I was only ever doing tests for setting individual attributes). Modified: trunk/SQLObject/sqlobject/dbconnection.py =================================================================== --- trunk/SQLObject/sqlobject/dbconnection.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/dbconnection.py 2005-02-20 09:33:10 UTC (rev 627) @@ -275,7 +275,7 @@ ", ".join(select.tables)) else: columns = ", ".join(["%s.%s" % (cls.sqlmeta.table, col.dbName) - for col in cls._SO_columns]) + for col in cls.sqlmeta._columns]) if columns: q += "%s.%s, %s FROM %s WHERE " % \ (cls.sqlmeta.table, cls.sqlmeta.idName, columns, @@ -310,8 +310,8 @@ else: desc = False assert sqlbuilder.sqlIdentifier(s), "Strings in clauses are expected to be column identifiers. I got: %r" % s - if select.sourceClass._SO_columnDict.has_key(s): - s = select.sourceClass._SO_columnDict[s].dbName + if select.sourceClass.sqlmeta._columnDict.has_key(s): + s = select.sourceClass.sqlmeta._columnDict[s].dbName if desc: return sqlbuilder.DESC(sqlbuilder.SQLConstant(s)) else: @@ -365,7 +365,7 @@ def createColumns(self, soClass): columnDefs = [self.createIDColumn(soClass)] \ + [self.createColumn(soClass, col) - for col in soClass._SO_columns] + for col in soClass.sqlmeta._columns] return ",\n".join([" %s" % c for c in columnDefs]) def createColumn(self, soClass, col): @@ -464,27 +464,12 @@ self.sqlrepr(secondValue))) def _SO_columnClause(self, soClass, kw): - return ' AND '.join(['%s = %s' % - (soClass._SO_columnDict[key].dbName, - self.sqlrepr(value)) - for key, value - in kw.items()]) - terms = [] - for key, value in kw.items(): - if hasattr(value, '_SO_joinDict'): #handle an object value - # find the joinColumn - for join in value._SO_joinDict.values(): - if join.otherClass is soClass: - dbName = join.joinColumn - break - else: #if nothing found - raise TypeError, "Cannot selectBy(%s=%r)" % (key, value) - value = value.id - else: - dbName = soClass._SO_columnDict[key].dbName - term = '%s = %s' % (dbName, self.sqlrepr(value)) - terms.append(term) - return ' AND '.join(terms) + return ' AND '.join( + ['%s = %s' % + (soClass.sqlmeta._columnDict[key].dbName, + self.sqlrepr(value)) + for key, value + in kw.items()]) def sqlrepr(self, v): return sqlrepr(v, self.dbName) Modified: trunk/SQLObject/sqlobject/index.py =================================================================== --- trunk/SQLObject/sqlobject/index.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/index.py 2005-02-20 09:33:10 UTC (rev 627) @@ -37,7 +37,7 @@ columnName = desc['column'] if not isinstance(columnName, str): columnName = columnName.name - colDict = self.soClass._SO_columnDict + colDict = self.soClass.sqlmeta._columnDict if not colDict.has_key(columnName): for possible in colDict.values(): if possible.origName == columnName: Modified: trunk/SQLObject/sqlobject/inheritance/iteration.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/iteration.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/inheritance/iteration.py 2005-02-20 09:33:10 UTC (rev 627) @@ -12,7 +12,7 @@ self._results = [] #phd: find the index of the childName column childNameIdx = None - columns = select.sourceClass._SO_columns + columns = select.sourceClass.sqlmeta._columns for i in range(len(columns)): #phd: enumerate() is unavailable python 2.2 if columns[i].name == "childName": childNameIdx = i Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/main.py 2005-02-20 09:33:10 UTC (rev 627) @@ -127,7 +127,7 @@ def findDependantColumns(name, klass): depends = [] - for col in klass._SO_columns: + for col in klass.sqlmeta._columns: if col.foreignKey == name and col.cascade is not None: depends.append(col) return depends @@ -159,8 +159,23 @@ __metaclass__ = declarative.DeclarativeMeta # These attributes shouldn't be shared with superclasses: - _unshared_attributes = ['table'] + _unshared_attributes = ['table', 'idName'] + # These are internal bookkeeping attributes; the class-level + # definition is a default for the instances, instances will + # reset these values. + + # When an object is being created, it has an instance + # variable _creating, which is true. This way all the + # setters can be captured until the object is complete, + # and then the row is inserted into the database. Once + # that happens, _creating is deleted from the instance, + # and only the class variable (which is always false) is + # left. + _creating = False + _obsolete = False + _perConnection = False + def __classinit__(cls, new_attrs): for attr in cls._unshared_attributes: if not new_attrs.has_key(attr): @@ -180,6 +195,30 @@ cls.table = cls.style.pythonClassToDBTable(cls.soClass.__name__) if cls.idName is None: cls.idName = cls.style.idForTable(cls.table) + + # plainSetters are columns that haven't been overridden by the + # user, so we can contact the database directly to set them. + # Note that these can't set these in the SQLObject class + # itself, because they specific to this subclass of SQLObject, + # and cannot be shared among classes. + cls._plainSetters = {} + cls._plainGetters = {} + cls._plainForeignSetters = {} + cls._plainForeignGetters = {} + cls._plainJoinGetters = {} + cls._plainJoinAdders = {} + cls._plainJoinRemovers = {} + + # This is a dictionary of columnName: columnObject + cls._columnDict = {} + cls._columns = [] + + # We keep track of the different joins by index, + # putting them in this list. + cls._joinList = [] + cls._joinDict = {} + cls._indexList = [] + setClass = classmethod(setClass) class _sqlmeta_attr(object): @@ -223,16 +262,6 @@ __metaclass__ = declarative.DeclarativeMeta - # When an object is being created, it has an instance - # variable _SO_creating, which is true. This way all the - # setters can be captured until the object is complete, - # and then the row is inserted into the database. Once - # that happens, _SO_creating is deleted from the instance, - # and only the class variable (which is always false) is - # left. - _SO_creating = False - _SO_obsolete = False - # Sometimes an intance is attached to a connection, not # globally available. In that case, self._SO_perConnection # will be true. It's false by default: @@ -417,23 +446,6 @@ if connection or not hasattr(cls, '_connection'): cls.setConnection(connection) - # plainSetters are columns that haven't been overridden by the - # user, so we can contact the database directly to set them. - # Note that these can't set these in the SQLObject class - # itself, because they specific to this subclass of SQLObject, - # and cannot be shared among classes. - cls._SO_plainSetters = {} - cls._SO_plainGetters = {} - cls._SO_plainForeignSetters = {} - cls._SO_plainForeignGetters = {} - cls._SO_plainJoinGetters = {} - cls._SO_plainJoinAdders = {} - cls._SO_plainJoinRemovers = {} - - # This is a dictionary of columnName: columnObject - cls._SO_columnDict = {} - cls._SO_columns = [] - # We have to check if there are columns in the inherited # _columns where the attribute has been set to None in this # class. If so, then we need to remove that column from @@ -451,11 +463,6 @@ ######################################## # Now we do the joins: - # We keep track of the different joins by index, - # putting them in this list. - cls._SO_joinList = [] - cls._SO_joinDict = {} - for join in cls._joins: cls.addJoin(join) @@ -464,7 +471,6 @@ cls._SO_finishedClassCreation = True makeProperties(cls) - cls._SO_indexList = [] for idx in cls._indexes: cls.addIndex(idx) @@ -535,15 +541,15 @@ def addIndex(cls, indexDef): index = indexDef.withClass(cls) - cls._SO_indexList.append(index) + cls.sqlmeta._indexList.append(index) addIndex = classmethod(addIndex) def addColumn(cls, columnDef, changeSchema=False, connection=None): column = columnDef.withClass(cls) name = column.name assert name != 'id', "The 'id' column is implicit, and should not be defined as a column" - cls._SO_columnDict[name] = column - cls._SO_columns.append(column) + cls.sqlmeta._columnDict[name] = column + cls.sqlmeta._columns.append(column) if columnDef not in cls._columns: cls._columns.append(columnDef) @@ -572,7 +578,7 @@ # _SO_get_columnName definition. if not hasattr(cls, getterName(name)) or (name == 'childName'): setattr(cls, getterName(name), getter) - cls._SO_plainGetters[name] = 1 + cls.sqlmeta._plainGetters[name] = 1 ################################################# # Create the setter function(s) @@ -593,7 +599,7 @@ # We keep track of setters that haven't been # overridden, because we can combine these # set columns into one SQL UPDATE query. - cls._SO_plainSetters[name] = 1 + cls.sqlmeta._plainSetters[name] = 1 ################################################## # Here we check if the column is a foreign key, in @@ -623,7 +629,7 @@ # (sans ID ending) if not hasattr(cls, getterName(name)[:-2]): setattr(cls, getterName(name)[:-2], getter) - cls._SO_plainForeignGetters[name[:-2]] = 1 + cls.sqlmeta._plainForeignGetters[name[:-2]] = 1 if not column.immutable: # The setter just gets the ID of the object, @@ -632,7 +638,7 @@ setattr(cls, rawSetterName(name)[:-2], setter) if not hasattr(cls, setterName(name)[:-2]): setattr(cls, setterName(name)[:-2], setter) - cls._SO_plainForeignSetters[name[:-2]] = 1 + cls.sqlmeta._plainForeignSetters[name[:-2]] = 1 # We'll need to put in a real reference at # some point. See needSet at the top of the @@ -670,28 +676,28 @@ def delColumn(cls, column, changeSchema=False, connection=None): if isinstance(column, str): - column = cls._SO_columnDict[column] + column = cls.sqlmeta._columnDict[column] if isinstance(column, col.Col): - for c in cls._SO_columns: + for c in cls.sqlmeta._columns: if column is c.columnDef: column = c break - cls._SO_columns.remove(column) + cls.sqlmeta._columns.remove(column) cls._columns.remove(column.columnDef) name = column.name - del cls._SO_columnDict[name] + del cls.sqlmeta._columnDict[name] delattr(cls, rawGetterName(name)) - if cls._SO_plainGetters.has_key(name): + if cls.sqlmeta._plainGetters.has_key(name): delattr(cls, getterName(name)) delattr(cls, rawSetterName(name)) - if cls._SO_plainSetters.has_key(name): + if cls.sqlmeta._plainSetters.has_key(name): delattr(cls, setterName(name)) if column.foreignKey: delattr(cls, rawGetterName(name)[:-2]) - if cls._SO_plainForeignGetters.has_key(name[:-2]): + if cls.sqlmeta._plainForeignGetters.has_key(name[:-2]): delattr(cls, getterName(name)[:-2]) delattr(cls, rawSetterName(name)[:-2]) - if cls._SO_plainForeignSetters.has_key(name[:-2]): + if cls.sqlmeta._plainForeignSetters.has_key(name[:-2]): delattr(cls, setterName(name)[:-2]) if column.alternateMethodName: delattr(cls, column.alternateMethodName) @@ -711,23 +717,23 @@ # join class. join = joinDef.withClass(cls) meth = join.joinMethodName - cls._SO_joinDict[joinDef] = join + cls.sqlmeta._joinDict[joinDef] = join - cls._SO_joinList.append(join) - index = len(cls._SO_joinList)-1 + cls.sqlmeta._joinList.append(join) + index = len(cls.sqlmeta._joinList)-1 if joinDef not in cls._joins: cls._joins.append(joinDef) # The function fetches the join by index, and # then lets the join object do the rest of the # work: - func = eval('lambda self: self._SO_joinList[%i].performJoin(self)' % index) + func = eval('lambda self: self.sqlmeta._joinList[%i].performJoin(self)' % index) # And we do the standard _SO_get_... _get_... deal setattr(cls, rawGetterName(meth), func) if not hasattr(cls, getterName(meth)): setattr(cls, getterName(meth), func) - cls._SO_plainJoinGetters[meth] = 1 + cls.sqlmeta._plainJoinGetters[meth] = 1 # Some joins allow you to remove objects from the # join. @@ -735,21 +741,21 @@ # Again, we let it do the remove, and we do the # standard naming trick. - func = eval('lambda self, obj: self._SO_joinList[%i].remove(self, obj)' % index) + func = eval('lambda self, obj: self.sqlmeta._joinList[%i].remove(self, obj)' % index) setattr(cls, '_SO_remove' + join.addRemoveName, func) if not hasattr(cls, 'remove' + join.addRemoveName): setattr(cls, 'remove' + join.addRemoveName, func) - cls._SO_plainJoinRemovers[meth] = 1 + cls.sqlmeta._plainJoinRemovers[meth] = 1 # Some joins allow you to add objects. if hasattr(join, 'add'): # And again... - func = eval('lambda self, obj: self._SO_joinList[%i].add(self, obj)' % (len(cls._SO_joinList)-1)) + func = eval('lambda self, obj: self.sqlmeta._joinList[%i].add(self, obj)' % (len(cls.sqlmeta._joinList)-1)) setattr(cls, '_SO_add' + join.addRemoveName, func) if not hasattr(cls, 'add' + join.addRemoveName): setattr(cls, 'add' + join.addRemoveName, func) - cls._SO_plainJoinAdders[meth] = 1 + cls.sqlmeta._plainJoinAdders[meth] = 1 if cls._SO_finishedClassCreation: makeProperties(cls) @@ -757,25 +763,25 @@ addJoin = classmethod(addJoin) def delJoin(cls, joinDef): - join = cls._SO_joinDict[joinDef] + join = cls.sqlmeta._joinDict[joinDef] meth = join.joinMethodName cls._joins.remove(joinDef) - del cls._SO_joinDict[joinDef] - for i in range(len(cls._SO_joinList)): - if cls._SO_joinList[i] is joinDef: + del cls.sqlmeta._joinDict[joinDef] + for i in range(len(cls.sqlmeta._joinList)): + if cls.sqlmeta._joinList[i] is joinDef: # Have to leave None, because we refer to joins # by index. - cls._SO_joinList[i] = None + cls.sqlmeta._joinList[i] = None delattr(cls, rawGetterName(meth)) - if cls._SO_plainJoinGetters.has_key(meth): + if cls.sqlmeta._plainJoinGetters.has_key(meth): delattr(cls, getterName(meth)) if hasattr(join, 'remove'): delattr(cls, '_SO_remove' + join.addRemovePrefix) - if cls._SO_plainJoinRemovers.has_key(meth): + if cls.sqlmeta._plainJoinRemovers.has_key(meth): delattr(cls, 'remove' + join.addRemovePrefix) if hasattr(join, 'add'): delattr(cls, '_SO_add' + join.addRemovePrefix) - if cls._SO_plainJoinAdders.has_key(meth): + if cls.sqlmeta._plainJoinAdders.has_key(meth): delattr(cls, 'add' + join.addRemovePrefix) if cls._SO_finishedClassCreation: @@ -806,7 +812,7 @@ self._SO_perConnection = True if not selectResults: - dbNames = [col.dbName for col in self._SO_columns] + dbNames = [col.dbName for col in self.sqlmeta._columns] selectResults = self._connection._SO_selectOne(self, dbNames) if not selectResults: raise SQLObjectNotFound, "The object %s by the ID %s does not exist" % (self.__class__.__name__, self.id) @@ -833,7 +839,7 @@ else: return result self._expired = False - dbNames = [col.dbName for col in self._SO_columns] + dbNames = [col.dbName for col in self.sqlmeta._columns] selectResults = self._connection._SO_selectOne(self, dbNames) if not selectResults: raise SQLObjectNotFound, "The object %s by the ID %s has been deleted" % (self.__class__.__name__, self.id) @@ -848,7 +854,7 @@ self.syncUpdate() self._SO_writeLock.acquire() try: - dbNames = [col.dbName for col in self._SO_columns] + dbNames = [col.dbName for col in self.sqlmeta._columns] selectResults = self._connection._SO_selectOne(self, dbNames) if not selectResults: raise SQLObjectNotFound, "The object %s by the ID %s has been deleted" % (self.__class__.__name__, self.id) @@ -862,8 +868,9 @@ return self._SO_writeLock.acquire() try: - if self._SO_columnDict: - values = [(self._SO_columnDict[v[0]].dbName, v[1]) for v in self._SO_createValues.items()] + if self.sqlmeta._columnDict: + values = [(self.sqlmeta._columnDict[v[0]].dbName, v[1]) + for v in self._SO_createValues.items()] self._connection._SO_update(self, values) self.dirty = False self._SO_createValues = {} @@ -877,7 +884,7 @@ try: if self._expired: return - for column in self._SO_columns: + for column in self.sqlmeta._columns: delattr(self, instanceName(column.name)) self._expired = True self._connection.cache.expire(self.id, self.__class__) @@ -888,7 +895,7 @@ # This is the place where we actually update the # database. - # If we are _SO_creating, the object doesn't yet exist + # If we are _creating, the object doesn't yet exist # in the database, and we can't insert it until all # the parts are set. So we just keep them in a # dictionary until later: @@ -898,15 +905,15 @@ dbValue = value if toPython: value = toPython(dbValue, self._SO_validatorState) - if self._SO_creating or self.sqlmeta.lazyUpdate: + if self.sqlmeta._creating or self.sqlmeta.lazyUpdate: self.dirty = True self._SO_createValues[name] = dbValue setattr(self, instanceName(name), value) return - self._connection._SO_update(self, - [(self._SO_columnDict[name].dbName, - dbValue)]) + self._connection._SO_update( + self, [(self.sqlmeta._columnDict[name].dbName, + dbValue)]) if self.sqlmeta.cacheValues: setattr(self, instanceName(name), value) @@ -918,15 +925,15 @@ # Filter out items that don't map to column names. # Those will be set directly on the object using # setattr(obj, name, value). - is_column = self._SO_plainSetters.has_key + is_column = self.sqlmeta._plainSetters.has_key f_is_column = lambda item: is_column(item[0]) f_not_column = lambda item: not is_column(item[0]) items = kw.items() extra = dict(filter(f_not_column, items)) kw = dict(filter(f_is_column, items)) - # _SO_creating is special, see _SO_setValue - if self._SO_creating or self.sqlmeta.lazyUpdate: + # _creating is special, see _SO_setValue + if self.sqlmeta._creating or self.sqlmeta.lazyUpdate: for name, value in kw.items(): fromPython = getattr(self, '_SO_fromPython_%s' % name, None) if fromPython: @@ -941,7 +948,7 @@ try: getattr(self.__class__, name) except AttributeError: - if name not in self._SO_columnDict: + if name not in self.sqlmeta._columnDict: raise TypeError, "%s.set() got an unexpected keyword argument %s" % (self.__class__.__name__, name) try: setattr(self, name, value) @@ -973,14 +980,14 @@ toPython = getattr(self, '_SO_toPython_%s' % name, None) if toPython: value = toPython(dbValue, self._SO_validatorState) - if self._cacheValues: + if self.sqlmeta.cacheValues: setattr(self, instanceName(name), value) toUpdate[name] = dbValue for name, value in extra.items(): try: getattr(self.__class__, name) except AttributeError: - if name not in self._SO_columnDict: + if name not in self.sqlmeta._columnDict: raise TypeError, "%s.set() got an unexpected keyword argument %s" % (self.__class__.__name__, name) try: setattr(self, name, value) @@ -988,25 +995,26 @@ raise AttributeError, '%s (with attribute %r)' % (e, name) if toUpdate: - args = [(self._SO_columnDict[name].dbName, value) + args = [(self.sqlmeta._columnDict[name].dbName, value) for name, value in toUpdate.items()] self._connection._SO_update(self, args) finally: self._SO_writeLock.release() def _SO_selectInit(self, row): - for col, colValue in zip(self._SO_columns, row): + for col, colValue in zip(self.sqlmeta._columns, row): if col.toPython: colValue = col.toPython(colValue, self._SO_validatorState) setattr(self, instanceName(col.name), colValue) def _SO_getValue(self, name): # Retrieves a single value from the database. Simple. - assert not self._SO_obsolete, "%s with id %s has become obsolete" \ - % (self.__class__.__name__, self.id) + assert not self.sqlmeta._obsolete, ( + "%s with id %s has become obsolete" \ + % (self.__class__.__name__, self.id)) # @@: do we really need this lock? #self._SO_writeLock.acquire() - column = self._SO_columnDict[name] + column = self.sqlmeta._columnDict[name] results = self._connection._SO_selectOne(self, [column.dbName]) #self._SO_writeLock.release() assert results != None, "%s with id %s is not in the database" \ @@ -1050,13 +1058,13 @@ def _create(self, id, **kw): - self._SO_creating = True + self.sqlmeta._creating = True self._SO_createValues = {} self._SO_validatorState = SQLObjectState(self) # First we do a little fix-up on the keywords we were # passed: - for column in self._SO_columns: + for column in self.sqlmeta._columns: # If a foreign key is given, we get the ID of the object # and put that in instead @@ -1087,7 +1095,7 @@ # to be set, but were delayed until now: setters = self._SO_createValues.items() # Here's their database names: - names = [self._SO_columnDict[v[0]].dbName for v in setters] + names = [self.sqlmeta._columnDict[v[0]].dbName for v in setters] values = [v[1] for v in setters] # Get rid of _SO_create*, we aren't creating anymore. # Doesn't have to be threadsafe because we're still in @@ -1097,7 +1105,7 @@ del self._SO_createValues else: self._SO_createValues = {} - del self._SO_creating + del self.sqlmeta._creating # Do the insert -- most of the SQL in this case is left # up to DBConnection, since getting a new ID is @@ -1115,7 +1123,7 @@ result = (connection or cls._connection)._SO_selectOneAlt( cls, [cls.sqlmeta.idName] + - [col.dbName for col in cls._SO_columns], + [col.dbName for col in cls.sqlmeta._columns], dbIDName, value) if not result: @@ -1212,7 +1220,7 @@ def createIndexes(cls, ifNotExists=False, connection=None): conn = connection or cls._connection - for index in cls._SO_indexList: + for index in cls.sqlmeta._indexList: if not index: continue conn._SO_createIndex(cls, index) @@ -1220,7 +1228,7 @@ def _getJoinsToCreate(cls): joins = [] - for join in cls._SO_joinList: + for join in cls.sqlmeta._joinList: if not join: continue if not join.hasIntermediateTable(): @@ -1233,7 +1241,7 @@ def dropJoinTables(cls, ifExists=False, connection=None): conn = connection or cls._connection - for join in cls._SO_joinList: + for join in cls.sqlmeta._joinList: if not join: continue if not join.hasIntermediateTable(): @@ -1279,7 +1287,7 @@ (klass.__name__, self.id, k.__name__)) for row in results: row.destroySelf() - self._SO_obsolete = True + self.sqlmeta._obsolete = True self._connection._SO_delete(self) self._connection.cache.expire(self.id, self.__class__) @@ -1310,7 +1318,7 @@ def _reprItems(self): items = [] - for col in self._SO_columns: + for col in self.sqlmeta._columns: value = getattr(self, col.name) r = repr(value) if len(r) > 20: Modified: trunk/SQLObject/sqlobject/sqlbuilder.py =================================================================== --- trunk/SQLObject/sqlobject/sqlbuilder.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/sqlbuilder.py 2005-02-20 09:33:10 UTC (rev 627) @@ -341,7 +341,7 @@ return SQLObjectField(self.tableName, self.soClass.sqlmeta.idName, attr) else: return SQLObjectField(self.tableName, - self.soClass._SO_columnDict[attr].dbName, + self.soClass.sqlmeta._columnDict[attr].dbName, attr) class Field(SQLExpression): Modified: trunk/SQLObject/sqlobject/sresults.py =================================================================== --- trunk/SQLObject/sqlobject/sresults.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/sresults.py 2005-02-20 09:33:10 UTC (rev 627) @@ -36,8 +36,8 @@ else: desc = False if isinstance(orderBy, (str, unicode)): - if self.sourceClass._SO_columnDict.has_key(orderBy): - val = self.sourceClass._SO_columnDict[orderBy].dbName + if self.sourceClass.sqlmeta._columnDict.has_key(orderBy): + val = self.sourceClass.sqlmeta._columnDict[orderBy].dbName if desc: return '-' + val else: Modified: trunk/SQLObject/sqlobject/tests/test_basic.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_basic.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/tests/test_basic.py 2005-02-20 09:33:10 UTC (rev 627) @@ -44,6 +44,8 @@ assert bob.name == 'bob' bob.name = 'joe' assert bob.name == 'joe' + bob.set(name='joebob', passwd='testtest') + assert bob.name == 'joebob' class TestSO2(SQLObject): name = StringCol(length=50, dbName='name_col') Modified: trunk/SQLObject/sqlobject/tests/test_style.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_style.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/tests/test_style.py 2005-02-20 09:33:10 UTC (rev 627) @@ -25,5 +25,5 @@ st1 = SOStyleTest1(a='something', st2=None) st2 = SOStyleTest2(b='whatever') st1.st2 = st2 - assert st1._SO_columnDict['st2ID'].dbName == 'idst2' + assert st1.sqlmeta._columnDict['st2ID'].dbName == 'idst2' assert st1.st2 == st2 Modified: trunk/SQLObject/sqlobject/tests/test_style_old.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_style_old.py 2005-02-20 04:55:21 UTC (rev 626) +++ trunk/SQLObject/sqlobject/tests/test_style_old.py 2005-02-20 09:33:10 UTC (rev 627) @@ -25,7 +25,7 @@ st1 = OldSOStyleTest1(a='something', st2=None) st2 = OldSOStyleTest2(b='whatever') st1.st2 = st2 - assert st1._SO_columnDict['st2ID'].dbName == 'idst2' + assert st1.sqlmeta._columnDict['st2ID'].dbName == 'idst2' assert st1.st2 == st2 teardown_module() |
From: <sub...@co...> - 2005-02-20 04:55:24
|
Author: ianb Date: 2005-02-20 04:55:21 +0000 (Sun, 20 Feb 2005) New Revision: 626 Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py trunk/SQLObject/sqlobject/inheritance/iteration.py trunk/SQLObject/sqlobject/joins.py trunk/SQLObject/sqlobject/main.py trunk/SQLObject/sqlobject/tests/test_auto.py Log: Moved _registry into sqlmeta Modified: trunk/SQLObject/sqlobject/inheritance/__init__.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-20 04:49:42 UTC (rev 625) +++ trunk/SQLObject/sqlobject/inheritance/__init__.py 2005-02-20 04:55:21 UTC (rev 626) @@ -31,7 +31,8 @@ #DSM: and will do himself the relationship between classes. if type(clause) is not str: tableRegistry = {} - allClasses = classregistry.registry(sourceClass._registry).allClasses() + allClasses = classregistry.registry( + sourceClass.sqlmeta.registry).allClasses() for registryClass in allClasses: if registryClass.sqlmeta.table in tablesDict: #DSM: By default, no parents are needed for the clauses Modified: trunk/SQLObject/sqlobject/inheritance/iteration.py =================================================================== --- trunk/SQLObject/sqlobject/inheritance/iteration.py 2005-02-20 04:49:42 UTC (rev 625) +++ trunk/SQLObject/sqlobject/inheritance/iteration.py 2005-02-20 04:55:21 UTC (rev 626) @@ -64,7 +64,7 @@ dbconn = self.dbconn rawconn = self.rawconn cursor = rawconn.cursor() - registry = self.select.sourceClass._registry + registry = self.select.sourceClass.sqlmeta.registry for childName, ids in childIdsNames.items(): klass = findClass(childName, registry) select = klass.select(sqlbuilder.IN(sqlbuilder.SQLConstant("id"), ids)) Modified: trunk/SQLObject/sqlobject/joins.py =================================================================== --- trunk/SQLObject/sqlobject/joins.py 2005-02-20 04:49:42 UTC (rev 625) +++ trunk/SQLObject/sqlobject/joins.py 2005-02-20 04:55:21 UTC (rev 626) @@ -54,7 +54,7 @@ joinDef=None): self.soClass = soClass self.otherClassName = otherClass - classregistry.registry(soClass._registry).addClassCallback( + classregistry.registry(soClass.sqlmeta.registry).addClassCallback( otherClass, self._setOtherClass) self.joinColumn = joinColumn self.joinMethodName = joinMethodName @@ -145,7 +145,8 @@ self.intermediateTable = intermediateTable self.otherColumn = otherColumn SOMultipleJoin.__init__(self, **kw) - classregistry.registry(self.soClass._registry).addClassCallback( + classregistry.registry( + self.soClass.sqlmeta.registry).addClassCallback( self.otherClassName, self._setOtherRelatedClass) def _setOtherRelatedClass(self, otherClass): Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-20 04:49:42 UTC (rev 625) +++ trunk/SQLObject/sqlobject/main.py 2005-02-20 04:55:21 UTC (rev 626) @@ -154,6 +154,7 @@ lazyUpdate = False defaultOrder = None cacheValues = True + registry = None __metaclass__ = declarative.DeclarativeMeta @@ -247,8 +248,6 @@ _fromDatabase = False - _registry = None - # Default is false, but we set it to true for the *instance* # when necessary: (bad clever? maybe) _expired = False @@ -484,7 +483,7 @@ setattr(cls.q, column.name, getattr(currentClass.q, column.name)) - classregistry.registry(cls._registry).addClass(cls) + classregistry.registry(cls.sqlmeta.registry).addClass(cls) _style = _sqlmeta_attr('style', 2) _table = _sqlmeta_attr('table', 2) @@ -492,10 +491,11 @@ _lazyUpdate = _sqlmeta_attr('lazyUpdate', 2) _defaultOrder = _sqlmeta_attr('defaultOrder', 2) _cacheValues = _sqlmeta_attr('cacheValues', 2) + _registry = _sqlmeta_attr('registry', 2) def _cleanDeprecatedAttrs(cls, new_attrs): for attr in ['_table', '_lazyUpdate', '_style', '_idName', - '_defaultOrder', '_cacheValues']: + '_defaultOrder', '_cacheValues', '_registry']: if new_attrs.has_key(attr): new_name = attr[1:] deprecated("'%s' is deprecated; please set the '%s' " @@ -637,7 +637,7 @@ # We'll need to put in a real reference at # some point. See needSet at the top of the # file for more on this. - classregistry.registry(cls._registry).addClassCallback( + classregistry.registry(cls.sqlmeta.registry).addClassCallback( column.foreignKey, lambda foreign, me, attr: setattr(me, attr, foreign), cls, '_SO_class_%s' % column.foreignKey) @@ -1134,7 +1134,7 @@ _SO_fetchAlternateID = classmethod(_SO_fetchAlternateID) def _SO_depends(cls): - return findDependencies(cls.__name__, cls._registry) + return findDependencies(cls.__name__, cls.sqlmeta.registry) _SO_depends = classmethod(_SO_depends) def select(cls, clause=None, clauseTables=None, Modified: trunk/SQLObject/sqlobject/tests/test_auto.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_auto.py 2005-02-20 04:49:42 UTC (rev 625) +++ trunk/SQLObject/sqlobject/tests/test_auto.py 2005-02-20 04:55:21 UTC (rev 626) @@ -160,4 +160,5 @@ assert jane.wannahavefun assert john.longField == 'x'*1000 assert jane.longField == 'x'*1000 - del classregistry.registry(AutoTest._registry).classes['AutoTest'] + del classregistry.registry( + AutoTest.sqlmeta.registry).classes['AutoTest'] |
From: <sub...@co...> - 2005-02-20 04:49:47
|
Author: ianb Date: 2005-02-20 04:49:42 +0000 (Sun, 20 Feb 2005) New Revision: 625 Modified: trunk/SQLObject/sqlobject/main.py trunk/SQLObject/sqlobject/tests/test_basic.py Log: Moved cacheValues into sqlmeta Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-20 04:45:59 UTC (rev 624) +++ trunk/SQLObject/sqlobject/main.py 2005-02-20 04:49:42 UTC (rev 625) @@ -153,6 +153,7 @@ style = None lazyUpdate = False defaultOrder = None + cacheValues = True __metaclass__ = declarative.DeclarativeMeta @@ -236,11 +237,6 @@ # will be true. It's false by default: _SO_perConnection = False - # The _cacheValues attribute controls if you cache - # values fetched from the database. We make sure - # it's set (default 1). - _cacheValues = True - _connection = None _columns = [] @@ -495,10 +491,11 @@ _idName = _sqlmeta_attr('idName', 2) _lazyUpdate = _sqlmeta_attr('lazyUpdate', 2) _defaultOrder = _sqlmeta_attr('defaultOrder', 2) + _cacheValues = _sqlmeta_attr('cacheValues', 2) def _cleanDeprecatedAttrs(cls, new_attrs): for attr in ['_table', '_lazyUpdate', '_style', '_idName', - '_defaultOrder']: + '_defaultOrder', '_cacheValues']: if new_attrs.has_key(attr): new_name = attr[1:] deprecated("'%s' is deprecated; please set the '%s' " @@ -558,7 +555,7 @@ # we'll alias that to _SO_get_columnName. This # allows a sort of super call, even though there's # no superclass that defines the database access. - if cls._cacheValues: + if cls.sqlmeta.cacheValues: # We create a method here, which is just a function # that takes "self" as the first argument. getter = eval('lambda self: self._SO_loadValue(%s)' % repr(instanceName(name))) @@ -609,7 +606,7 @@ # deal, except chopping off the "ID" ending since # we're giving the object, not the ID of the # object this time: - if cls._cacheValues: + if cls.sqlmeta.cacheValues: # self._SO_class_className is a reference # to the class in question. getter = eval('lambda self: self._SO_foreignKey(self._SO_loadValue(%r), self._SO_class_%s)' % (instanceName(name), column.foreignKey)) @@ -911,7 +908,7 @@ [(self._SO_columnDict[name].dbName, dbValue)]) - if self._cacheValues: + if self.sqlmeta.cacheValues: setattr(self, instanceName(name), value) def set(self, **kw): @@ -1127,7 +1124,7 @@ obj = cls.get(result[0], connection=connection) else: obj = cls.get(result[0]) - if not obj._cacheValues: + if not obj.sqlmeta.cacheValues: obj._SO_writeLock.acquire() try: obj._SO_selectInit(result[1:]) Modified: trunk/SQLObject/sqlobject/tests/test_basic.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_basic.py 2005-02-20 04:45:59 UTC (rev 624) +++ trunk/SQLObject/sqlobject/tests/test_basic.py 2005-02-20 04:49:42 UTC (rev 625) @@ -4,9 +4,11 @@ class TestSO1(SQLObject): name = StringCol(length=50, dbName='name_col') - _cacheValues = False passwd = StringCol(length=10) + class sqlmeta: + cacheValues = False + def _set_passwd(self, passwd): self._SO_set_passwd(passwd.encode('rot13')) |
From: <sub...@co...> - 2005-02-20 04:46:03
|
Author: ianb Date: 2005-02-20 04:45:59 +0000 (Sun, 20 Feb 2005) New Revision: 624 Modified: trunk/SQLObject/sqlobject/joins.py trunk/SQLObject/sqlobject/main.py trunk/SQLObject/sqlobject/sresults.py trunk/SQLObject/sqlobject/tests/test_auto.py trunk/SQLObject/sqlobject/tests/test_joins.py trunk/SQLObject/sqlobject/tests/test_sorting.py trunk/SQLObject/sqlobject/tests/test_transactions.py Log: Moved defaultOrder into sqlmeta Modified: trunk/SQLObject/sqlobject/joins.py =================================================================== --- trunk/SQLObject/sqlobject/joins.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/joins.py 2005-02-20 04:45:59 UTC (rev 624) @@ -74,7 +74,7 @@ def _applyOrderBy(self, results, defaultSortClass): if self.orderBy is NoDefault: - self.orderBy = defaultSortClass._defaultOrder + self.orderBy = defaultSortClass.sqlmeta.defaultOrder if self.orderBy is not None: results.sort(sorter(self.orderBy)) return results Modified: trunk/SQLObject/sqlobject/main.py =================================================================== --- trunk/SQLObject/sqlobject/main.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/main.py 2005-02-20 04:45:59 UTC (rev 624) @@ -152,6 +152,7 @@ idName = None style = None lazyUpdate = False + defaultOrder = None __metaclass__ = declarative.DeclarativeMeta @@ -204,11 +205,11 @@ # 2) Deprecated after 1 (0.8?) # 3) Deprecated after 2 (0.9?) -def deprecated(message, level=1): +def deprecated(message, level=1, stacklevel=2): if exception_level is not None and exception_level <= level: raise NotImplementedError(message) if warnings_level is not None and warnings_level <= level: - warnings.warn(message, DeprecationWarning, stacklevel=2) + warnings.warn(message, DeprecationWarning, stacklevel=stacklevel) # SQLObject is the superclass for all SQLObject classes, of # course. All the deeper magic is done in MetaSQLObject, and @@ -240,9 +241,6 @@ # it's set (default 1). _cacheValues = True - # The _defaultOrder is used by SelectResults - _defaultOrder = None - _connection = None _columns = [] @@ -496,14 +494,17 @@ _table = _sqlmeta_attr('table', 2) _idName = _sqlmeta_attr('idName', 2) _lazyUpdate = _sqlmeta_attr('lazyUpdate', 2) + _defaultOrder = _sqlmeta_attr('defaultOrder', 2) def _cleanDeprecatedAttrs(cls, new_attrs): - for attr in ['_table', '_lazyUpdate', '_style', '_idName']: + for attr in ['_table', '_lazyUpdate', '_style', '_idName', + '_defaultOrder']: if new_attrs.has_key(attr): new_name = attr[1:] deprecated("'%s' is deprecated; please set the '%s' " "attribute in sqlmeta instead" % - (attr, new_name), level=2) + (attr, new_name), level=2, + stacklevel=5) setattr(cls.sqlmeta, new_name, new_attrs[attr]) delattr(cls, attr) Modified: trunk/SQLObject/sqlobject/sresults.py =================================================================== --- trunk/SQLObject/sqlobject/sresults.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/sresults.py 2005-02-20 04:45:59 UTC (rev 624) @@ -19,7 +19,7 @@ self.tables = tablesDict.keys() self.ops = ops if self.ops.get('orderBy', sqlbuilder.NoDefault) is sqlbuilder.NoDefault: - self.ops['orderBy'] = sourceClass._defaultOrder + self.ops['orderBy'] = sourceClass.sqlmeta.defaultOrder orderBy = self.ops['orderBy'] if isinstance(orderBy, list) or isinstance(orderBy, tuple): orderBy = map(self._mungeOrderBy, orderBy) Modified: trunk/SQLObject/sqlobject/tests/test_auto.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_auto.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/tests/test_auto.py 2005-02-20 04:45:59 UTC (rev 624) @@ -13,13 +13,15 @@ class Person(SQLObject): + class sqlmeta: + defaultOrder = 'name' _columns = [StringCol('name', length=100, dbName='name_col')] - _defaultOrder = 'name' class Phone(SQLObject): + class sqlmeta: + defaultOrder = 'phone' _columns = [StringCol('phone', length=12)] - _defaultOrder = 'phone' class TestPeople: @@ -34,7 +36,7 @@ def test_defaultOrder(self): assert (list(Person.select('all')) == - list(Person.select('all', orderBy=Person._defaultOrder))) + list(Person.select('all', orderBy=Person.sqlmeta.defaultOrder))) def test_dynamicColumn(self): if not supports('dynamicColumn'): Modified: trunk/SQLObject/sqlobject/tests/test_joins.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_joins.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/tests/test_joins.py 2005-02-20 04:45:59 UTC (rev 624) @@ -68,10 +68,12 @@ class AddressJoiner2(SQLObject): + class sqlmeta: + defaultOrder = ['-zip', 'plus4'] + _columns = [StringCol('zip', length=5), StringCol('plus4', length=4, default=None), ForeignKey('PersonJoiner2')] - _defaultOrder = ['-zip', 'plus4'] class TestJoin2: Modified: trunk/SQLObject/sqlobject/tests/test_sorting.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_sorting.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/tests/test_sorting.py 2005-02-20 04:45:59 UTC (rev 624) @@ -5,11 +5,11 @@ class sqlmeta(sqlmeta): table = 'names_table' + defaultOrder = ['lastName', 'firstName'] firstName = StringCol(length=30) lastName = StringCol(length=30) - _defaultOrder = ['lastName', 'firstName'] def setupNames(): setupClass(Names) Modified: trunk/SQLObject/sqlobject/tests/test_transactions.py =================================================================== --- trunk/SQLObject/sqlobject/tests/test_transactions.py 2005-02-20 04:45:46 UTC (rev 623) +++ trunk/SQLObject/sqlobject/tests/test_transactions.py 2005-02-20 04:45:59 UTC (rev 624) @@ -7,8 +7,9 @@ class TestSOTrans(SQLObject): #_cacheValues = False + class sqlmeta: + defaultOrder = 'name' name = StringCol(length=10, alternateID=True, dbName='name_col') - _defaultOrderBy = 'name' def test_transaction(): if not supports('transactions'): |