1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28 """Default field attributes for various sqlalchemy column types"""
29
30 import sqlalchemy.types
31 import camelot.types
32 from camelot.core.sql import like_op
33 from sqlalchemy.sql.operators import between_op
34 import datetime
35 import operator
36
37 from controls import delegates
38 from camelot.core import constants
39 from camelot.view.utils import (
40 bool_from_string,
41 date_from_string,
42 time_from_string,
43 datetime_from_string,
44 int_from_string,
45 float_from_string,
46 string_from_string,
47 enumeration_to_string,
48 )
49
50 _numerical_operators = (operator.eq, operator.ne, operator.lt, operator.le, operator.gt, operator.ge, between_op)
51 _text_operators = (operator.eq, operator.ne, like_op)
52
53 _sqlalchemy_to_python_type_ = {
54
55 sqlalchemy.types.Boolean: lambda f: {
56 'python_type': bool,
57 'editable': True,
58 'nullable': True,
59 'delegate': delegates.BoolDelegate,
60 'from_string': bool_from_string,
61 'operators' : (operator.eq,),
62 },
63
64 sqlalchemy.types.BOOLEAN: lambda f: {
65 'python_type': bool,
66 'editable': True,
67 'nullable': True,
68 'delegate': delegates.BoolDelegate,
69 'from_string': bool_from_string,
70 'operators' : (operator.eq,),
71 },
72
73 sqlalchemy.types.Date: lambda f: {
74 'python_type': datetime.date,
75 'format': constants.camelot_date_format,
76 'editable': True,
77 'min': None,
78 'max': None,
79 'nullable': True,
80 'delegate': delegates.DateDelegate,
81 'from_string': date_from_string,
82 'operators' : _numerical_operators,
83 },
84
85 sqlalchemy.types.Time : lambda f: {
86 'python_type': datetime.time,
87 'editable': True,
88 'nullable': True,
89 'widget': 'time',
90 'delegate': delegates.TimeDelegate,
91 'format': constants.camelot_time_format,
92 'nullable': True,
93 'from_string': time_from_string,
94 'operators': _numerical_operators,
95 },
96
97 sqlalchemy.types.DateTime : lambda f: {
98 'python_type': datetime.datetime,
99 'editable': True,
100 'nullable': True,
101 'widget': 'time',
102 'format': constants.camelot_datetime_format,
103 'nullable': True,
104 'delegate': delegates.DateTimeDelegate,
105 'from_string': datetime_from_string,
106 'operators': _numerical_operators,
107 },
108
109 sqlalchemy.types.Float: lambda f: {
110 'python_type': float,
111 'precision': f.precision if not isinstance(f.precision, tuple) else f.precision[1],
112 'editable': True,
113 'minimum': constants.camelot_minfloat,
114 'maximum': constants.camelot_maxfloat,
115 'nullable': True,
116 'delegate': delegates.FloatDelegate,
117 'from_string': float_from_string,
118 'operators': _numerical_operators,
119 },
120
121 sqlalchemy.types.Numeric: lambda f: {
122 'python_type': float,
123 'precision': f.scale,
124 'editable': True,
125 'minimum': constants.camelot_minfloat,
126 'maximum': constants.camelot_maxfloat,
127 'nullable': True,
128 'delegate': delegates.FloatDelegate,
129 'from_string': float_from_string,
130 'operators': _numerical_operators,
131 },
132
133 sqlalchemy.types.Integer: lambda f: {
134 'python_type': int,
135 'editable': True,
136 'minimum': constants.camelot_minint,
137 'maximum': constants.camelot_maxint,
138 'nullable': True,
139 'delegate': delegates.IntegerDelegate,
140 'from_string': int_from_string,
141 'to_string': unicode,
142 'widget': 'int',
143 'operators': _numerical_operators,
144 },
145
146 sqlalchemy.types.INT: lambda f: {
147 'python_type': int,
148 'editable': True,
149 'minimum': constants.camelot_minint,
150 'maximum': constants.camelot_maxint,
151 'nullable': True,
152 'delegate': delegates.IntegerDelegate,
153 'from_string': int_from_string,
154 'widget': 'int',
155 'operators': _numerical_operators,
156 },
157
158 sqlalchemy.types.String: lambda f: {
159 'python_type': str,
160 'length': f.length,
161 'delegate': delegates.PlainTextDelegate,
162 'editable': True,
163 'nullable': True,
164 'widget': 'str',
165 'from_string': string_from_string,
166 'operators' : _text_operators,
167 },
168
169 sqlalchemy.types.TEXT: lambda f: {
170 'python_type': str,
171 'length': f.length,
172 'delegate': delegates.PlainTextDelegate,
173 'editable': True,
174 'nullable': True,
175 'widget': 'str',
176 'from_string': string_from_string,
177 'operators' : _text_operators,
178 },
179
180 sqlalchemy.types.Unicode: lambda f: {
181 'python_type': str,
182 'length': f.length,
183 'delegate': delegates.PlainTextDelegate,
184 'editable': True,
185 'nullable': True,
186 'widget': 'str',
187 'from_string': string_from_string,
188 'operators' : _text_operators,
189 },
190
191 camelot.types.Image: lambda f: {
192 'python_type': str,
193 'editable': True,
194 'nullable': True,
195 'delegate': delegates.ImageDelegate,
196 'storage': f.storage,
197 'preview_width': 100,
198 'preview_height': 100,
199 'operators' : _text_operators,
200 },
201
202 camelot.types.Code: lambda f: {
203 'python_type': str,
204 'editable': True,
205 'delegate': delegates.CodeDelegate,
206 'nullable': True,
207 'parts': f.parts,
208 'separator': f.separator,
209 'operators' : _text_operators,
210 },
211
212 camelot.types.IPAddress: lambda f: {
213 'python_type': str,
214 'editable': True,
215 'nullable': True,
216 'parts': f.parts,
217 'delegate': delegates.CodeDelegate,
218 'widget': 'code',
219 'operators' : _text_operators,
220 },
221
222 camelot.types.VirtualAddress: lambda f: {
223 'python_type': str,
224 'editable': True,
225 'nullable': True,
226 'delegate': delegates.VirtualAddressDelegate,
227 'operators' : _text_operators,
228 },
229
230 camelot.types.RichText: lambda f: {
231 'python_type': str,
232 'editable': True,
233 'nullable': True,
234 'delegate': delegates.RichTextDelegate,
235 'from_string': string_from_string,
236 'operators' : [],
237 },
238
239 camelot.types.Color: lambda f: {
240 'delegate': delegates.ColorDelegate,
241 'python_type': str,
242 'editable': True,
243 'nullable': True,
244 'widget': 'color',
245 'operators' : _text_operators,
246 },
247
248 camelot.types.Rating: lambda f: {
249 'delegate': delegates.StarDelegate,
250 'editable': True,
251 'nullable': True,
252 'python_type': int,
253 'widget': 'star',
254 'from_string': int_from_string,
255 'operators' : _numerical_operators,
256 },
257
258 camelot.types.Enumeration: lambda f: {
259 'delegate': delegates.EnumerationDelegate,
260 'python_type': str,
261 'choices': [(v, enumeration_to_string(v)) for v in f.choices],
262 'from_string': lambda s:dict((enumeration_to_string(v), v) for v in f.choices)[s],
263 'editable': True,
264 'nullable': False,
265 'widget': 'combobox',
266 'operators' : _numerical_operators,
267 },
268
269 camelot.types.Language: lambda f: {
270 'delegate': delegates.EnumerationDelegate,
271 'python_type': str,
272 'choices': f.choices,
273 'from_string': string_from_string,
274 'editable': True,
275 'nullable': False,
276 'widget': 'combobox',
277 },
278
279 camelot.types.File : lambda f: {
280 'python_type': str,
281 'editable': True,
282 'delegate': delegates.FileDelegate,
283 'storage': f.storage,
284 'operators' : _text_operators,
285 },
286 }
287
288
289
290
291
294 self.length = 20
295 self.parts = ['AAA', '99']
296 self.choices = ['planned', 'canceled']
297 self.precision = 2
298 self.scale = 2
299 self.storage = None
300 self.separator = u'.'
301
302 row_separator = '+' + '-'*20 + '+' + '-'*70 + '+' + '-'*70 + '+'
303 row_format = """| %-18s | %-68s | %-68s |"""
304
305 doc = """Field types handled through introspection :
306
307 """ + row_separator + """
308 """ + row_format%('**Field type**', '**Default delegate**', '**Default editor**') + """
309 """ + row_separator + """
310 """
311
312 field_types = _sqlalchemy_to_python_type_.keys()
313 field_types.sort(lambda x, y: cmp(x.__name__, y.__name__))
314
315 for field_type in field_types:
316 field_attributes = _sqlalchemy_to_python_type_[field_type](DummyField())
317 delegate = field_attributes['delegate']
318 row = row_format%(field_type.__name__,
319 ':ref:`%s <delegate-%s>`'%(delegate.__name__, delegate.__name__),
320 '.. image:: ../_static/editors/%s_editable.png'%(delegate.editor.__name__))
321 doc += row + """
322 """ + row_separator + """
323 """
324
325 doc += """
326 """
327
328 __doc__ = doc
329