33 |
import sys |
import sys |
34 |
|
|
35 |
from gnue.common.apps import GDebug, GConfig |
from gnue.common.apps import GDebug, GConfig |
|
from gnue.common.apps import GDebug, GConfig |
|
36 |
from gnue.common.datasources import GIntrospection |
from gnue.common.datasources import GIntrospection |
37 |
|
|
38 |
class Introspection(GIntrospection.Introspection): |
class Introspection(GIntrospection.Introspection): |
|
pass |
|
39 |
|
_primaryKeyFields = [] |
40 |
|
|
41 |
|
# |
42 |
|
# Schema (metadata) functions |
43 |
|
# |
44 |
|
|
45 |
|
# Return a list of the types of Schema objects this driver provides |
46 |
|
def getSchemaTypes(self): |
47 |
|
return [('view',_('Views'),1), |
48 |
|
('table',_('Tables'),1)] |
49 |
|
|
50 |
|
# Return a list of Schema objects |
51 |
|
def getSchemaList(self, type=None): |
52 |
|
|
53 |
|
# This excludes any system tables and views. |
54 |
|
statement = "select rdb$relation_name, rdb$view_source "+\ |
55 |
|
"from rdb$relations " + \ |
56 |
|
"where rdb$system_flag=0 " + \ |
57 |
|
"order by rdb$relation_name" |
58 |
|
|
59 |
|
cursor = self._dataConnection.cursor() |
60 |
|
cursor.execute(statement) |
61 |
|
|
62 |
|
# TODO: rdb$view_source is null for table and rdb$view_source is not null for view |
63 |
|
list = [] |
64 |
|
for rs in cursor.fetchall(): |
65 |
|
list.append(GDataObjects.Schema(attrs={'id':rs[0], 'name':rstrip(rs[0]), |
66 |
|
'type':'table', |
67 |
|
'primarykey': self.__getPrimaryKey(rstrip(rs[0]))}, |
68 |
|
getChildSchema=self.__getFieldSchema)) |
69 |
|
|
70 |
|
cursor.close() |
71 |
|
return list |
72 |
|
|
73 |
|
# Find a schema object with specified name |
74 |
|
def getSchemaByName(self, name, type=None): |
75 |
|
|
76 |
|
statement = "select rdb$relation_name, rdb$view_source "+\ |
77 |
|
"from rdb$relations " + \ |
78 |
|
"where rdb$relation_name = '%s'" % (name) |
79 |
|
|
80 |
|
cursor = self._dataConnection.cursor() |
81 |
|
cursor.execute(statement) |
82 |
|
|
83 |
|
rs = cursor.fetchone() |
84 |
|
if rs: |
85 |
|
schema = GDataObjects.Schema(attrs={'id':rs[0], 'name':rstrip(rs[0]), |
86 |
|
'type':'table', |
87 |
|
'primarykey': self.__getPrimaryKey(rstrip(rs[0]))}, |
88 |
|
getChildSchema=self.__getFieldSchema) |
89 |
|
else: |
90 |
|
schema = None |
91 |
|
|
92 |
|
cursor.close() |
93 |
|
return schema |
94 |
|
|
95 |
|
# Return a list of fields (for _buildDeleteStatement and for _buildUpdateStatement) |
96 |
|
def __getPrimaryKey(self, relname): |
97 |
|
statement = "select rdb$relation_name, rdb$field_name, "+\ |
98 |
|
"rdb$constraint_name, rdb$field_position "+\ |
99 |
|
"from rdb$relation_constraints rc, rdb$index_segments ri "+\ |
100 |
|
"where ri.rdb$index_name = rc.rdb$index_name "+\ |
101 |
|
"and rc.rdb$constraint_type = 'PRIMARY KEY' "+\ |
102 |
|
"and rc.rdb$relation_name = '%s' " % (relname)+\ |
103 |
|
"order by ri.rdb$field_position" |
104 |
|
|
105 |
|
cursor = self._dataConnection.cursor() |
106 |
|
cursor.execute(statement) |
107 |
|
|
108 |
|
list = [] |
109 |
|
for rs in cursor.fetchall(): |
110 |
|
list.append(lower(rstrip(rs[1]))) |
111 |
|
|
112 |
|
cursor.close() |
113 |
|
return list |
114 |
|
|
115 |
|
# Get fields for a table |
116 |
|
def __getFieldSchema(self, parent): |
117 |
|
|
118 |
|
statement = "select * from %s"%(parent.name) + " where (0=1)" |
119 |
|
|
120 |
|
cursor = self._dataConnection.cursor() |
121 |
|
cursor.execute(statement) |
122 |
|
|
123 |
|
list = [] |
124 |
|
|
125 |
|
for d in cursor.description: |
126 |
|
try: |
127 |
|
nativetype = lower(d[SIG2api.DESCRIPTION_TYPE_CODE].__name__) |
128 |
|
except AttributeError: |
129 |
|
nativetype='unknown' |
130 |
|
|
131 |
|
attrs={'id':d[SIG2api.DESCRIPTION_NAME], |
132 |
|
'name':lower(d[SIG2api.DESCRIPTION_NAME]), |
133 |
|
'type':'field', |
134 |
|
'nativetype': nativetype, |
135 |
|
'required': d[SIG2api.DESCRIPTION_NULL_OK]==0, |
136 |
|
'length': d[SIG2api.DESCRIPTION_DISPLAY_SIZE]} |
137 |
|
|
138 |
|
if nativetype in ('int','float','long'): |
139 |
|
attrs['datatype']='number' |
140 |
|
attrs['precision']=d[SIG2api.DESCRIPTION_SCALE] |
141 |
|
elif nativetype == 'tuple': |
142 |
|
attrs['datatype']='date' |
143 |
|
else: |
144 |
|
attrs['datatype']='text' |
145 |
|
|
146 |
|
cursor.execute("select rdb$default_source from rdb$relation_fields"+ \ |
147 |
|
" where rdb$relation_name = '%s' " % (parent.name)+ \ |
148 |
|
" and rdb$field_name = '%s'" % (upper(attrs['name']))) |
149 |
|
defrs = cursor.fetchone() |
150 |
|
if defrs[0]: |
151 |
|
dflt = defrs[0] |
152 |
|
if dflt[9:12] == "NOW": |
153 |
|
attrs['defaulttype'] = 'timestamp' |
154 |
|
else: |
155 |
|
attrs['defaulttype'] = 'constant' |
156 |
|
attrs['defaultval'] = dflt[8:] |
157 |
|
|
158 |
|
list.append(GDataObjects.Schema(attrs=attrs)) |
159 |
|
|
160 |
|
cursor.close() |
161 |
|
return list |