[Zope-CVS] CVS: Products/Ape/lib/apelib/sql -
classification.py:1.8.2.3 dbapi.py:1.11.2.4
interfaces.py:1.4.2.4 mysql.py:1.1.4.2 properties.py:1.11.2.3
sqlbase.py:1.13.2.4 structure.py:1.11.2.3 table.py:1.1.2.4
Shane Hathaway
shane at zope.com
Wed Jul 21 02:07:34 EDT 2004
Update of /cvs-repository/Products/Ape/lib/apelib/sql
In directory cvs.zope.org:/tmp/cvs-serv25827/sql
Modified Files:
Tag: sql-types-branch
classification.py dbapi.py interfaces.py mysql.py
properties.py sqlbase.py structure.py table.py
Log Message:
Fixed bugs in sql-types-branch. The tests now pass.
=== Products/Ape/lib/apelib/sql/classification.py 1.8.2.2 => 1.8.2.3 ===
--- Products/Ape/lib/apelib/sql/classification.py:1.8.2.2 Tue Jul 20 22:25:58 2004
+++ Products/Ape/lib/apelib/sql/classification.py Wed Jul 21 02:07:34 2004
@@ -46,11 +46,12 @@
return classification, rec
def store(self, event, classification):
+ conn = self.get_connection(event)
table = self.get_table(event)
row = (classification.get('class_name', ''),
classification.get('mapper_name', ''))
try:
table.set_one(event.oid, self.column_names, row, event.is_new)
- except conn.module.IntegrityError:
+ except conn.module.DatabaseError:
raise OIDConflictError(event.oid)
return row
=== Products/Ape/lib/apelib/sql/dbapi.py 1.11.2.3 => 1.11.2.4 ===
--- Products/Ape/lib/apelib/sql/dbapi.py:1.11.2.3 Wed Jul 21 00:55:47 2004
+++ Products/Ape/lib/apelib/sql/dbapi.py Wed Jul 21 02:07:34 2004
@@ -22,7 +22,7 @@
from apelib.core.interfaces import ITPCConnection
from apelib.core.schemas import ColumnSchema
-from apelib.sql.interfaces import ISQLConnection
+from apelib.sql.interfaces import ISQLConnection, IRDBMSColumn
from apelib.sql.table import SQLTable
name_style_re = re.compile(':[A-Za-z0-9_-]+')
@@ -37,7 +37,6 @@
# factories by column name take precedence over factories by column type.
column_factories_by_name = {} # { local col name -> column factory }
- column_factories_by_type = {} # { local type name -> column factory }
column_name_translations = {} # { local col name -> db col name }
column_type_translations = {} # { local type name -> db type name }
module = None
@@ -66,23 +65,21 @@
def define_table(self, name, schema):
"""Creates and returns an IRDBMSTable."""
- t = SQLTable(self, self.prefix + name)
+ table = SQLTable(self, self.prefix + name)
for c in schema.get_columns():
factory = self.column_factories_by_name.get(c.name, None)
if factory is None:
- factory = self.column_factories_by_type.get(c.type, None)
- if factory is None:
factory = RDBMSColumn
- dbc = factory(c)
- name = self.column_name_translations.get(c.name)
- if name is not None:
- dbc.name = name
- type = self.column_name_translations.get(c.type)
- if type is not None:
- dbc.type = type
- t.add_column(c.name, dbc)
- self._tables[name] = t
- return t
+ dbc = factory(self, c)
+ n = self.column_name_translations.get(c.name)
+ if n is not None:
+ dbc.name = n
+ t = self.column_type_translations.get(c.type)
+ if t is not None:
+ dbc.type = t
+ table.add_column(c.name, dbc)
+ self._tables[name] = table
+ return table
def get_table(self, name):
"""Returns a previously defined IRDBMSTable."""
@@ -115,6 +112,11 @@
"""
raise NotImplementedError("Abstract Method")
+ def clear_table(self, name):
+ """Removes all rows from a table.
+ """
+ self.execute('DELETE FROM %s' % (self.prefix + name))
+
def execute(self, sql, kw=None, fetch=False):
if self.connector is None:
raise RuntimeError('Not connected')
@@ -256,15 +258,17 @@
"""Basic RDBMS column. Does no type translation."""
__implements__ = IRDBMSColumn
- def __init__(self, column):
+ use_conversion = False
+
+ def __init__(self, connection, column):
self.name = column.name
self.type = column.type
self.unique = column.unique
- def to_db(self, connection, value):
+ def to_db(self, value):
return value
- def from_db(self, connection, value):
+ def from_db(self, value):
return value
@@ -272,17 +276,14 @@
"""RDBMS column that stores string OIDs as integers."""
__implements__ = IRDBMSColumn
- def to_db(self, connection, value):
+ use_conversion = True
+
+ def to_db(self, value):
return int(value)
- def from_db(self, connection, value):
+ def from_db(self, value):
return str(value)
# Set up default column types.
AbstractSQLConnection.column_factories_by_name['oid'] = OIDColumn
-
-
-# Names imported for backward compatibility only.
-from apelib.sql.postgresql import PostgreSQLConnection
-from apelib.sql.mysql import MySQLConnection
=== Products/Ape/lib/apelib/sql/interfaces.py 1.4.2.3 => 1.4.2.4 ===
--- Products/Ape/lib/apelib/sql/interfaces.py:1.4.2.3 Wed Jul 21 00:55:47 2004
+++ Products/Ape/lib/apelib/sql/interfaces.py Wed Jul 21 02:07:34 2004
@@ -64,6 +64,14 @@
Whether the value is before or after the increment is not specified.
"""
+ def clear_table(name):
+ """Removes all rows from a table.
+
+ This is not a method of IRDBMSTable because it is not
+ always possible to construct an IRDBMSTable while resetting
+ tables.
+ """
+
class ISQLConnection (IRDBMSConnection):
@@ -116,6 +124,9 @@
class IRDBMSColumn (IColumnSchema):
"""A column associated with a specific database."""
+
+ use_conversion = Attribute(
+ "use_conversion", "True if this column needs to convert values.")
def to_db(value):
"""Converts a generic value to a database-specific value."""
=== Products/Ape/lib/apelib/sql/mysql.py 1.1.4.1 => 1.1.4.2 ===
--- Products/Ape/lib/apelib/sql/mysql.py:1.1.4.1 Wed Jul 21 00:55:47 2004
+++ Products/Ape/lib/apelib/sql/mysql.py Wed Jul 21 02:07:34 2004
@@ -76,3 +76,4 @@
table_name)
rows = self.execute("SELECT LAST_INSERT_ID()", fetch=1)
return rows[0][0]
+
=== Products/Ape/lib/apelib/sql/properties.py 1.11.2.2 => 1.11.2.3 ===
--- Products/Ape/lib/apelib/sql/properties.py:1.11.2.2 Tue Jul 20 22:25:58 2004
+++ Products/Ape/lib/apelib/sql/properties.py Wed Jul 21 02:07:34 2004
@@ -77,7 +77,16 @@
self.table_name = table_name
self.schema = schema
SQLGatewayBase.__init__(self, conn_name)
+ self.columns = schema.get_columns()
+ def init(self, event):
+ conn = self.get_connection(event)
+ all = RowSequenceSchema(
+ self.oid_columns + self.table_schema.get_columns())
+ table = conn.define_table(self.table_name, all)
+ if not conn.exists(self.table_name, 'table'):
+ table.create()
+
def load(self, event):
table = self.get_table(event)
recs = table.select(self.column_names, oid=event.oid)
@@ -152,8 +161,9 @@
return None
def init(self, event):
- table = self.get_table(event)
- if not conn.exists(table.name, 'table'):
+ conn = self.get_connection(event)
+ table = conn.define_table(self.table_name, self.table_schema)
+ if not conn.exists(self.table_name, 'table'):
table.create()
self.var_props.init(event)
if event.clear_all:
@@ -209,13 +219,13 @@
module_name = cn[:pos]
class_name = cn[pos + 1:]
schema = self.get_schema_for_class(module_name, class_name)
- if not schema.get_columns():
+ if schema is None or not schema.get_columns():
# No fixed properties exist for this class.
self.fixed_props[cn] = None
return None
# Allocate a table name
- conn = self.get_connection()
+ conn = self.get_connection(event)
table = self.get_table(event)
rows = table.select(('table_name',), class_name=cn)
if rows:
=== Products/Ape/lib/apelib/sql/sqlbase.py 1.13.2.3 => 1.13.2.4 ===
--- Products/Ape/lib/apelib/sql/sqlbase.py:1.13.2.3 Wed Jul 21 00:55:47 2004
+++ Products/Ape/lib/apelib/sql/sqlbase.py Wed Jul 21 02:07:34 2004
@@ -16,7 +16,8 @@
$Id$
"""
-from apelib.core.interfaces import IGateway, IDatabaseInitializer
+from apelib.core.interfaces \
+ import IGateway, IDatabaseInitializer, IDatabaseInitEvent
from apelib.core.schemas import ColumnSchema, RowSequenceSchema
from interfaces import IRDBMSConnection
@@ -36,7 +37,7 @@
self.conn_name = conn_name
if self.table_schema is None:
if self.schema is not None:
- self.table_schema = schema
+ self.table_schema = self.schema
else:
self.table_schema = RowSequenceSchema()
self.column_names = [f.name for f in self.table_schema.get_columns()]
@@ -54,10 +55,11 @@
def init(self, event):
conn = self.get_connection(event)
assert IRDBMSConnection.isImplementedBy(conn)
- all = RowSequenceSchema(self.oid_columns + self.table_schema.get_columns())
+ all = RowSequenceSchema(
+ self.oid_columns + self.table_schema.get_columns())
table = conn.define_table(self.table_name, all)
if conn.exists(self.table_name, 'table'):
- if event.clear_all:
+ if IDatabaseInitEvent.isImplementedBy(event) and event.clear_all:
table.delete_rows()
else:
table.create()
=== Products/Ape/lib/apelib/sql/structure.py 1.11.2.2 => 1.11.2.3 ===
--- Products/Ape/lib/apelib/sql/structure.py:1.11.2.2 Tue Jul 20 22:25:58 2004
+++ Products/Ape/lib/apelib/sql/structure.py Wed Jul 21 02:07:34 2004
@@ -35,12 +35,13 @@
firstcol = self.column_names[:1]
items = table.select(firstcol, oid=event.oid)
if items:
- state = items[0][0]
+ state = str(items[0][0])
else:
state = ''
return state, state
def store(self, event, state):
+ conn = self.get_connection(event)
table = self.get_table(event)
firstcol = self.column_names[:1]
data = (conn.module.Binary(state),)
@@ -64,7 +65,7 @@
def load(self, event):
table = self.get_table(event)
- rows = table.select(self.columns, oid=event.oid)
+ rows = table.select(self.column_names, oid=event.oid)
res = []
h = []
for name, child_oid in rows:
@@ -139,7 +140,7 @@
def load(self, event):
table = self.get_table(event)
- items = table.select(self.columns, oid=event.oid)
+ items = table.select(self.column_names, oid=event.oid)
if items:
state = long(items[0][0])
else:
@@ -150,7 +151,7 @@
state = long(state)
table = self.get_table(event)
data = (state,)
- table.set_one(event.oid, self.columns, data, event.is_new)
+ table.set_one(event.oid, self.column_names, data, event.is_new)
return state
=== Products/Ape/lib/apelib/sql/table.py 1.1.2.3 => 1.1.2.4 ===
--- Products/Ape/lib/apelib/sql/table.py:1.1.2.3 Wed Jul 21 00:55:47 2004
+++ Products/Ape/lib/apelib/sql/table.py Wed Jul 21 02:07:34 2004
@@ -47,7 +47,7 @@
return ' AND '.join(clauses)
def generate_select(self, filter_col_names, result_col_names):
- result_names = [self.columns[col].name for col in col_names]
+ result_names = [self.columns[col].name for col in result_col_names]
sql = 'SELECT %s FROM %s' % (', '.join(result_names), self.name)
where = self.generate_conditions(filter_col_names)
if where:
@@ -97,14 +97,23 @@
f[col_name] = self.columns[col_name].to_db(value)
sql = self.cache(self.generate_select, filter.keys(), result_col_names)
db_res = self.execute(sql, f, fetch=1)
- # Convert the result to standard types.
- res = []
- dbcols = []
+ # Convert the results to standard types.
+ conversions = []
for n in range(len(result_col_names)):
- dbcols.append((n, self.columns[result_col_names[n]].from_db))
- for row in db_res:
- r = [from_db(row[n]) for (n, from_db) in dbcols]
- res.append(tuple(r))
+ col = self.columns[result_col_names[n]]
+ if col.use_conversion:
+ conversions.append((n, col.from_db))
+ if conversions:
+ # Convert specific columns.
+ res = []
+ for row in db_res:
+ r = list(row)
+ for n, from_db in conversions:
+ r[n] = from_db(r[n])
+ res.append(tuple(r))
+ else:
+ # No conversion needed.
+ res = db_res
return res
def insert(self, col_names, row):
@@ -196,10 +205,11 @@
"""Creates the table.
"""
pkeys = []
+ col_decls = []
for c in self.column_order:
col = self.columns[c]
constraints = ''
- if unique:
+ if col.unique:
constraints = ' NOT NULL'
pkeys.append(col.name)
col_decls.append(
More information about the Zope-CVS
mailing list