scipion-pyworkflow 3.10.5__py3-none-any.whl → 3.11.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (127) hide show
  1. pyworkflow/config.py +131 -67
  2. pyworkflow/constants.py +12 -2
  3. pyworkflow/object.py +3 -2
  4. pyworkflow/plugin.py +93 -44
  5. pyworkflow/project/scripts/fix_links.py +4 -1
  6. pyworkflow/resources/showj/arrowDown.png +0 -0
  7. pyworkflow/resources/showj/arrowUp.png +0 -0
  8. pyworkflow/resources/showj/background_section.png +0 -0
  9. pyworkflow/resources/showj/colRowModeOff.png +0 -0
  10. pyworkflow/resources/showj/colRowModeOn.png +0 -0
  11. pyworkflow/resources/showj/delete.png +0 -0
  12. pyworkflow/resources/showj/doc_icon.png +0 -0
  13. pyworkflow/resources/showj/download_icon.png +0 -0
  14. pyworkflow/resources/showj/enabled_gallery.png +0 -0
  15. pyworkflow/resources/showj/galleryViewOff.png +0 -0
  16. pyworkflow/resources/showj/galleryViewOn.png +0 -0
  17. pyworkflow/resources/showj/goto.png +0 -0
  18. pyworkflow/resources/showj/menu.png +0 -0
  19. pyworkflow/resources/showj/separator.png +0 -0
  20. pyworkflow/resources/showj/tableViewOff.png +0 -0
  21. pyworkflow/resources/showj/tableViewOn.png +0 -0
  22. pyworkflow/resources/showj/ui-bg_glass_75_e6e6e6_1x400.png +0 -0
  23. pyworkflow/resources/showj/ui-bg_glass_95_fef1ec_1x400.png +0 -0
  24. pyworkflow/resources/showj/ui-bg_highlight-soft_75_cccccc_1x100.png +0 -0
  25. pyworkflow/resources/showj/volumeOff.png +0 -0
  26. pyworkflow/resources/showj/volumeOn.png +0 -0
  27. pyworkflow/viewer.py +23 -1
  28. pyworkflowtests/objects.py +2 -2
  29. pyworkflowtests/protocols.py +1 -3
  30. {scipion_pyworkflow-3.10.5.dist-info → scipion_pyworkflow-3.11.0.dist-info}/METADATA +21 -25
  31. scipion_pyworkflow-3.11.0.dist-info/RECORD +71 -0
  32. {scipion_pyworkflow-3.10.5.dist-info → scipion_pyworkflow-3.11.0.dist-info}/WHEEL +1 -1
  33. scipion_pyworkflow-3.11.0.dist-info/entry_points.txt +2 -0
  34. pyworkflow/apps/__init__.py +0 -29
  35. pyworkflow/apps/pw_manager.py +0 -37
  36. pyworkflow/apps/pw_plot.py +0 -51
  37. pyworkflow/apps/pw_project.py +0 -113
  38. pyworkflow/apps/pw_protocol_list.py +0 -143
  39. pyworkflow/apps/pw_protocol_run.py +0 -51
  40. pyworkflow/apps/pw_run_tests.py +0 -267
  41. pyworkflow/apps/pw_schedule_run.py +0 -322
  42. pyworkflow/apps/pw_sleep.py +0 -37
  43. pyworkflow/apps/pw_sync_data.py +0 -439
  44. pyworkflow/apps/pw_viewer.py +0 -78
  45. pyworkflow/gui/__init__.py +0 -36
  46. pyworkflow/gui/browser.py +0 -726
  47. pyworkflow/gui/canvas.py +0 -1190
  48. pyworkflow/gui/dialog.py +0 -977
  49. pyworkflow/gui/form.py +0 -2637
  50. pyworkflow/gui/graph.py +0 -247
  51. pyworkflow/gui/graph_layout.py +0 -271
  52. pyworkflow/gui/gui.py +0 -566
  53. pyworkflow/gui/matplotlib_image.py +0 -233
  54. pyworkflow/gui/plotter.py +0 -247
  55. pyworkflow/gui/project/__init__.py +0 -25
  56. pyworkflow/gui/project/base.py +0 -192
  57. pyworkflow/gui/project/constants.py +0 -139
  58. pyworkflow/gui/project/labels.py +0 -205
  59. pyworkflow/gui/project/project.py +0 -492
  60. pyworkflow/gui/project/searchprotocol.py +0 -154
  61. pyworkflow/gui/project/searchrun.py +0 -181
  62. pyworkflow/gui/project/steps.py +0 -171
  63. pyworkflow/gui/project/utils.py +0 -332
  64. pyworkflow/gui/project/variables.py +0 -179
  65. pyworkflow/gui/project/viewdata.py +0 -472
  66. pyworkflow/gui/project/viewprojects.py +0 -510
  67. pyworkflow/gui/project/viewprotocols.py +0 -2093
  68. pyworkflow/gui/project/viewprotocols_extra.py +0 -560
  69. pyworkflow/gui/text.py +0 -771
  70. pyworkflow/gui/tooltip.py +0 -185
  71. pyworkflow/gui/tree.py +0 -684
  72. pyworkflow/gui/widgets.py +0 -307
  73. pyworkflow/mapper/__init__.py +0 -26
  74. pyworkflow/mapper/mapper.py +0 -222
  75. pyworkflow/mapper/sqlite.py +0 -1578
  76. pyworkflow/mapper/sqlite_db.py +0 -145
  77. pyworkflow/project/__init__.py +0 -31
  78. pyworkflow/project/config.py +0 -454
  79. pyworkflow/project/manager.py +0 -180
  80. pyworkflow/project/project.py +0 -2010
  81. pyworkflow/protocol/__init__.py +0 -38
  82. pyworkflow/protocol/bibtex.py +0 -48
  83. pyworkflow/protocol/constants.py +0 -87
  84. pyworkflow/protocol/executor.py +0 -455
  85. pyworkflow/protocol/hosts.py +0 -313
  86. pyworkflow/protocol/launch.py +0 -270
  87. pyworkflow/protocol/package.py +0 -42
  88. pyworkflow/protocol/params.py +0 -741
  89. pyworkflow/protocol/protocol.py +0 -2582
  90. pyworkflow/tests/__init__.py +0 -29
  91. pyworkflow/tests/test_utils.py +0 -25
  92. pyworkflow/tests/tests.py +0 -341
  93. pyworkflow/utils/__init__.py +0 -38
  94. pyworkflow/utils/dataset.py +0 -414
  95. pyworkflow/utils/echo.py +0 -104
  96. pyworkflow/utils/graph.py +0 -169
  97. pyworkflow/utils/log.py +0 -284
  98. pyworkflow/utils/path.py +0 -528
  99. pyworkflow/utils/process.py +0 -132
  100. pyworkflow/utils/profiler.py +0 -92
  101. pyworkflow/utils/progressbar.py +0 -154
  102. pyworkflow/utils/properties.py +0 -631
  103. pyworkflow/utils/reflection.py +0 -129
  104. pyworkflow/utils/utils.py +0 -879
  105. pyworkflow/utils/which.py +0 -229
  106. pyworkflow/webservices/__init__.py +0 -8
  107. pyworkflow/webservices/config.py +0 -11
  108. pyworkflow/webservices/notifier.py +0 -162
  109. pyworkflow/webservices/repository.py +0 -59
  110. pyworkflow/webservices/workflowhub.py +0 -74
  111. pyworkflowtests/tests/__init__.py +0 -0
  112. pyworkflowtests/tests/test_canvas.py +0 -72
  113. pyworkflowtests/tests/test_domain.py +0 -45
  114. pyworkflowtests/tests/test_logs.py +0 -74
  115. pyworkflowtests/tests/test_mappers.py +0 -392
  116. pyworkflowtests/tests/test_object.py +0 -507
  117. pyworkflowtests/tests/test_project.py +0 -42
  118. pyworkflowtests/tests/test_protocol_execution.py +0 -135
  119. pyworkflowtests/tests/test_protocol_export.py +0 -78
  120. pyworkflowtests/tests/test_protocol_output.py +0 -158
  121. pyworkflowtests/tests/test_streaming.py +0 -47
  122. pyworkflowtests/tests/test_utils.py +0 -210
  123. scipion_pyworkflow-3.10.5.dist-info/RECORD +0 -140
  124. scipion_pyworkflow-3.10.5.dist-info/dependency_links.txt +0 -1
  125. scipion_pyworkflow-3.10.5.dist-info/entry_points.txt +0 -5
  126. {scipion_pyworkflow-3.10.5.dist-info → scipion_pyworkflow-3.11.0.dist-info/licenses}/LICENSE.txt +0 -0
  127. {scipion_pyworkflow-3.10.5.dist-info → scipion_pyworkflow-3.11.0.dist-info}/top_level.txt +0 -0
pyworkflow/gui/widgets.py DELETED
@@ -1,307 +0,0 @@
1
- # **************************************************************************
2
- # *
3
- # * Authors: J.M. De la Rosa Trevin (delarosatrevin@scilifelab.se) [1]
4
- # *
5
- # * [1] SciLifeLab, Stockholm University
6
- # *
7
- # * This program is free software: you can redistribute it and/or modify
8
- # * it under the terms of the GNU General Public License as published by
9
- # * the Free Software Foundation, either version 3 of the License, or
10
- # * (at your option) any later version.
11
- # *
12
- # * This program is distributed in the hope that it will be useful,
13
- # * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
- # * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
- # * GNU General Public License for more details.
16
- # *
17
- # * You should have received a copy of the GNU General Public License
18
- # * along with this program. If not, see <https://www.gnu.org/licenses/>.
19
- # *
20
- # * All comments concerning this program package may be sent to the
21
- # * e-mail address 'scipion@cnb.csic.es'
22
- # *
23
- # **************************************************************************
24
- """
25
- Some basic GUI widgets are implemented in this module.
26
- The widgets here are suppose to be used to build more complex
27
- elements.
28
- """
29
-
30
- import tkinter as tk
31
- import tkinter.ttk as ttk
32
-
33
- from math import ceil
34
-
35
- import pyworkflow
36
- from pyworkflow import TK_GRAY_DEFAULT, Config
37
-
38
- from . import gui
39
- from .tooltip import ToolTip
40
-
41
-
42
- class Button(tk.Button):
43
- _images = {}
44
-
45
- def __init__(self, master, text, imagePath=None, tooltip=None, **opts):
46
- defaults = {}
47
- # Used to be {'font': gui.fontButton} but there is no such
48
- # definition in pyworkflow/gui.
49
- defaults.update(opts)
50
-
51
- if 'bg' in defaults and defaults['bg'] is None:
52
- del defaults['bg']
53
-
54
- if imagePath is not None:
55
- btnImage = gui.getImage(imagePath)
56
- else:
57
- btnImage = None
58
-
59
- if btnImage is not None:
60
- if 'compound' not in defaults:
61
- defaults['compound'] = tk.LEFT
62
- tk.Button.__init__(self, master, text=text, image=btnImage, **defaults)
63
- self.image = btnImage
64
- else:
65
- tk.Button.__init__(self, master, text=text, **defaults)
66
-
67
- if tooltip:
68
- ToolTip(self, tooltip, 500)
69
-
70
- def setImage(self, imagePath):
71
- self.image = gui.getImage(imagePath)
72
- self.config(image=self.image)
73
-
74
-
75
- class HotButton(Button):
76
- """ Button having the firebrick color and some other settings. """
77
-
78
- def __init__(self, master, text, imagePath=None, tooltip=None, **opts):
79
- defaults = {'activebackground': gui.cfgButtonActiveBgColor, 'bg': gui.cfgButtonBgColor,
80
- 'fg': gui.cfgButtonFgColor, 'activeforeground': gui.cfgButtonActiveFgColor,
81
- 'compound': tk.LEFT}
82
- defaults.update(opts)
83
- Button.__init__(self, master, text, imagePath, tooltip, **defaults)
84
-
85
-
86
- class IconButton(HotButton):
87
- """ Hot button, but only with image and no border """
88
-
89
- def __init__(self, master, text, imagePath, tooltip=None, **opts):
90
- defaults = {'bd': 0, 'bg': Config.SCIPION_BG_COLOR, 'compound': tk.NONE}
91
- defaults.update(opts)
92
- HotButton.__init__(self, master, text, imagePath, tooltip, **defaults)
93
-
94
-
95
- class AutoScrollbar(tk.Scrollbar):
96
- """"A scrollbar that hides itself if it's not needed."""
97
-
98
- def set(self, lo, hi):
99
- if float(lo) <= 0.0 and float(hi) >= 1.0:
100
- self.grid_remove()
101
- # self.tk.call("grid", "remove", self)
102
- else:
103
- self.grid()
104
- tk.Scrollbar.set(self, lo, hi)
105
-
106
-
107
- class Scrollable(object):
108
- """This is a base class for all scrollable widgets.
109
- If it is enabled, it will wrap the widget with a frame
110
- and will add vertical and horizontal AutoScrollbar"""
111
-
112
- def __init__(self, master, WidgetClass, frame=True, **opts):
113
- if frame:
114
- self.frame = tk.Frame(master)
115
- self.frame.rowconfigure(0, weight=1)
116
- self.frame.columnconfigure(0, weight=1)
117
- self.vscroll = AutoScrollbar(self.frame)
118
- self.vscroll.grid(row=0, column=1, sticky='ns')
119
- self.hscroll = AutoScrollbar(self.frame, orient=tk.HORIZONTAL)
120
- self.hscroll.grid(row=1, column=0, sticky='ew')
121
- WidgetClass.__init__(self, self.frame,
122
- yscrollcommand=self.vscroll.set,
123
- xscrollcommand=self.hscroll.set, **opts)
124
- self.vscroll.config(command=self.yview)
125
- self.hscroll.config(command=self.xview)
126
- self.grid(row=0, column=0, sticky='news')
127
- self.grid = self.frame.grid
128
- self.grid_remove = self.frame.grid_remove
129
- else:
130
- WidgetClass.__init__(self, master, **opts)
131
-
132
- # Bind ourselves
133
- self.bindWidget(self)
134
-
135
-
136
- def scroll(self, event):
137
- print("Deprecated, use scrollV")
138
- self.scrollV(event)
139
-
140
- def scrollV(self, event):
141
- self._basescroll(event, self.yview)
142
-
143
- def scrollH(self, event):
144
- self._basescroll(event, self.xview)
145
-
146
- def _basescroll(self, event, view):
147
-
148
- if event.num == 5 or event.delta < 0:
149
- count = 1
150
- if event.num == 4 or event.delta > 0:
151
- count = -1
152
- view("scroll", count, "units")
153
-
154
- def bindWidget(self, widget):
155
- """ Make the scroll in the widget, respond to this.
156
- Useful for child widgets.
157
- """
158
- # with Windows OS
159
- widget.bind("<MouseWheel>", self.scrollV)
160
- # with Linux OS
161
- widget.bind("<Button-4>", self.scrollV)
162
- widget.bind("<Button-5>", self.scrollV)
163
-
164
- widget.bind("<Shift-Button-4>", self.scrollH)
165
- widget.bind("<Shift-Button-5>", self.scrollH)
166
-
167
-
168
- def getVScroll(self):
169
- return self.vscroll.get()
170
-
171
- def getHScroll(self):
172
- return self.hscroll.get()
173
-
174
-
175
- class ExplanationText(tk.Text):
176
- """Create an explanation text box"""
177
-
178
- def __init__(self, frame, text='', bg=TK_GRAY_DEFAULT, border=0, wrap='word'):
179
- self.text = tk.Text(frame, bg=bg, wrap=wrap, border=border)
180
- self.updateExpText(text)
181
-
182
- def updateExpText(self, text, width=50):
183
- # Adapt textbox height to text length (width is in characters)
184
- n_lines = ceil(len(text) / width)
185
-
186
- self.text.config(state='normal', height=n_lines) # Make it editable
187
- self.text.insert(tk.END, text)
188
- self.text.config(state='disabled') # Disable text edit
189
-
190
-
191
- class LabelSlider(ttk.Frame):
192
- """ Create a personalized frame that contains label, slider and label value
193
- it also keeps a variable with the value """
194
-
195
- def __init__(self, master, label, from_=0, to=100, value=50, callback=None, step=0.01, length=None,
196
- labelWidth=None, tickinterval=None, showvalue=None):
197
- self.selectedLabelText = '=> {}'.format(label)
198
- self.labelText = ' {}'.format(label)
199
- self.var = tk.DoubleVar()
200
- self.var.set(float(value))
201
- ttk.Frame.__init__(self, master)
202
- self.labelWidget = ttk.Label(self, text=self.labelText, width=labelWidth)
203
- self.slider = tk.Scale(self, from_=from_, to=to, variable=self.var,
204
- bigincrement=step, resolution=step, orient=tk.HORIZONTAL, length=length,
205
- tickinterval=tickinterval, showvalue=showvalue)
206
- if callback:
207
- self.var.trace('w', callback)
208
-
209
- self.labelWidget.grid(row=0, column=0, sticky='nes', padx=5, pady=5)
210
- self.slider.grid(row=0, column=1, sticky='news', padx=5, pady=5)
211
- self.columnconfigure(1, weight=3)
212
-
213
- def get(self):
214
- return self.var.get()
215
-
216
- def highlightLabel(self):
217
- self.labelWidget.config(text=self.selectedLabelText)
218
-
219
- def removeHighlightFromLabel(self):
220
- self.labelWidget.config(text=self.labelText)
221
-
222
-
223
- class ComboBox(ttk.Combobox):
224
- """ Extension of ttk.ComboBox to allow having different display text and values.
225
- Also adding some utils to getSelected index and value (same for set)
226
- """
227
-
228
- def __init__(self, parent, choices, values=None, initial=None, onChange=None, **kwargs):
229
- """ Create a combobox from a list of choices.
230
- Params:
231
- parent: the parent widget (required by Tkinter)
232
- choices: a list with the options to be shown.
233
- values: if None, will enumerate from 0 to len(choices)-1
234
- if a list is provided, should have the same length as choices.
235
- initial: if None, take the first choice
236
- onChange: provide a callback function to be used when change the selected value
237
- **kwargs: extra arguments passed to ttk.Combobox constructor.
238
- """
239
- indexes = range(len(choices))
240
- if values is None:
241
- values = indexes
242
- choices = [str(c) for c in choices] # Convert to a list of strings
243
-
244
- if initial is None:
245
- initial = choices[0]
246
- self._valuesDict = dict(zip(choices, values))
247
- self._indexDict = dict(zip(choices, indexes))
248
-
249
- self._var = tk.StringVar()
250
- self._var.set(initial)
251
- self._changeCallback = onChange
252
- self._var.trace('w', self._onChanged)
253
- ttk.Combobox.__init__(self, parent, textvariable=self._var, state='readonly', **kwargs)
254
- self['values'] = choices
255
-
256
- def getValue(self):
257
- """ Return the selected value. """
258
- return self._valuesDict[self._var.get()]
259
-
260
- def getIndex(self):
261
- """ Return the selected value. """
262
- return self._indexDict[self._var.get()]
263
-
264
- def getText(self):
265
- """ Return the selected option text. """
266
- return self._var.get()
267
-
268
- def setChangeCallback(self, callback):
269
- self._changeCallback = callback
270
-
271
- def _onChanged(self, *args):
272
- if self._changeCallback:
273
- self._changeCallback(self)
274
-
275
-
276
- class GradientFrame(tk.Canvas):
277
- """A gradient frame which uses a canvas to draw the background
278
- Taken from:
279
- http://stackoverflow.com/questions/11892521/tkinter-custom-window
280
- """
281
-
282
- def __init__(self, parent, **args):
283
- tk.Canvas.__init__(self, parent, **args)
284
- self._color1 = Config.SCIPION_BG_COLOR #"#d2a7a7"
285
- self._color2 = Config.SCIPION_MAIN_COLOR #"#820808"
286
- self.bind("<Configure>", self._draw_gradient)
287
-
288
- def _draw_gradient(self, event=None):
289
- self.delete("gradient")
290
- width = self.winfo_width()
291
- height = self.winfo_height()
292
- limit = width // 2
293
- r1, g1, b1 = self.winfo_rgb(self._color1)
294
- r2, g2, b2 = self.winfo_rgb(self._color2)
295
- r_ratio = (r2 - r1) / limit
296
- g_ratio = (g2 - g1) / limit
297
- b_ratio = (b2 - b1) / limit
298
-
299
- for i in range(limit + 1):
300
- nr = int(r1 + (r_ratio * i))
301
- ng = int(g1 + (g_ratio * i))
302
- nb = int(b1 + (b_ratio * i))
303
- color = "#%4.4x%4.4x%4.4x" % (nr, ng, nb)
304
- self.create_line(i, 0, i, height, tags=("gradient",), fill=color)
305
- self.create_line(width - i, 0, width - i, height,
306
- tags=("gradient",), fill=color)
307
- self.lower("gradient")
@@ -1,26 +0,0 @@
1
- # -*- coding: utf-8 -*-
2
- # **************************************************************************
3
- # *
4
- # * Authors: J.M. De la Rosa Trevin (delarosatrevin@scilifelab.se) [1]
5
- # *
6
- # * [1] SciLifeLab, Stockholm University
7
- # *
8
- # * This program is free software: you can redistribute it and/or modify
9
- # * it under the terms of the GNU General Public License as published by
10
- # * the Free Software Foundation, either version 3 of the License, or
11
- # * (at your option) any later version.
12
- # *
13
- # * This program is distributed in the hope that it will be useful,
14
- # * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
- # * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
- # * GNU General Public License for more details.
17
- # *
18
- # * You should have received a copy of the GNU General Public License
19
- # * along with this program. If not, see <https://www.gnu.org/licenses/>.
20
- # *
21
- # * All comments concerning this program package may be sent to the
22
- # * e-mail address 'scipion@cnb.csic.es'
23
- # *
24
- # **************************************************************************
25
- from .mapper import Mapper
26
- from .sqlite import SqliteMapper, SqliteDb, SqliteFlatMapper, SqliteFlatDb
@@ -1,222 +0,0 @@
1
- # **************************************************************************
2
- # *
3
- # * Authors: J.M. De la Rosa Trevin (jmdelarosa@cnb.csic.es)
4
- # *
5
- # * Unidad de Bioinformatica of Centro Nacional de Biotecnologia , CSIC
6
- # *
7
- # * This program is free software; you can redistribute it and/or modify
8
- # * it under the terms of the GNU General Public License as published by
9
- # * the Free Software Foundation; either version 3 of the License, or
10
- # * (at your option) any later version.
11
- # *
12
- # * This program is distributed in the hope that it will be useful,
13
- # * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
- # * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
- # * GNU General Public License for more details.
16
- # *
17
- # * You should have received a copy of the GNU General Public License
18
- # * along with this program; if not, write to the Free Software
19
- # * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
20
- # * 02111-1307 USA
21
- # *
22
- # * All comments concerning this program package may be sent to the
23
- # * e-mail address 'scipion@cnb.csic.es'
24
- # *
25
- # **************************************************************************
26
- import logging
27
- logger = logging.getLogger(__name__)
28
-
29
- import pyworkflow.object as obj
30
-
31
-
32
- class Mapper:
33
- """This class will serves as a Data Mapper pattern.
34
- It will store/retrieve objects from some storage environment.
35
- (like SQL, XML or others)
36
- The mapper should have access to class dictionary
37
- in order to build any give class by name"""
38
-
39
- # Just to avoid print several times the same warning
40
- __warnings = set()
41
-
42
- ORIGINAL_CLASS_NAME_ATTRIBUTE = "oldClassName"
43
-
44
- @staticmethod
45
- def annotateClassName(instance, oldClassName):
46
- """ Annotate an object with the original class name"""
47
- setattr(instance, Mapper.ORIGINAL_CLASS_NAME_ATTRIBUTE, oldClassName)
48
-
49
- @staticmethod
50
- def getObjectPersistingClassName(instance):
51
- if hasattr(instance, Mapper.ORIGINAL_CLASS_NAME_ATTRIBUTE):
52
- return getattr(instance, Mapper.ORIGINAL_CLASS_NAME_ATTRIBUTE)
53
- else:
54
- return instance.getClassName()
55
-
56
- def __init__(self, dictClasses=None):
57
- if dictClasses:
58
- self.dictClasses = dictClasses
59
- else:
60
- self.dictClasses = dir(obj)
61
-
62
- def warning(self, msg):
63
- if msg not in self.__warnings:
64
- print("WARNING: %s" % msg)
65
- self.__warnings.add(msg)
66
-
67
- def _buildObjectFromClass(self, className):
68
- """ Build an instance of an object
69
- given the class name, it should be in
70
- the classes' dictionary.
71
-
72
- If class is missing, then the default class is used ("LegacyProtocol") and warns about it
73
- """
74
- if className not in self.dictClasses:
75
- self.warning("Class '%s' not found in mapper dict. Ignored. "
76
- % className)
77
- return None
78
-
79
- objClass = self.dictClasses[className]
80
-
81
- if not issubclass(objClass, obj.Object):
82
- logger.warning("WARNING: Class '%s' is not a subclass of Object. Ignored. " % className)
83
- return None
84
-
85
- try:
86
- instance = self.dictClasses[className]()
87
- except Exception as e:
88
- clazz = self.dictClasses._default
89
- logger.error('Class %s could not be created. Replacing it with %s ' % (className, clazz.__name__), exc_info=e)
90
- instance = clazz()
91
-
92
- # If it's the default class in the dictionary
93
- if objClass.__name__ != className:
94
- # ... annotate original class name
95
- self.annotateClassName(instance, className)
96
-
97
- return instance
98
-
99
- def _getStrValue(self, value):
100
- """ Return empty string if value is None or empty. """
101
- if not value:
102
- return ''
103
- return value
104
-
105
- def commit(self):
106
- """Commit changes made to the storage"""
107
- pass
108
-
109
- def insert(self, obj):
110
- """Insert a new object into the system, the id will be set"""
111
- pass
112
-
113
- def update(self, obj, direction='to'):
114
- """Update an existing object, the id should not be None
115
- direction can be "to" or "from" which indicates the
116
- priority of the update.
117
- If "to" is used, object data is put in storage.
118
- If "from", object data is retrieved from storage"""
119
- if direction == 'to': # Update db with object changes
120
- self.updateTo(obj)
121
- elif direction == 'from': # Update object with db info
122
- self.updateFrom(obj)
123
- else:
124
- raise Exception('Invalid option %s for Sqlite.updateObject' % direction)
125
-
126
- def updateFrom(self, obj):
127
- """Update object data with storage info"""
128
- pass
129
-
130
- def updateTo(self, obj):
131
- """Update storage with object info"""
132
- pass
133
-
134
- def store(self, obj):
135
- """Stores an object, it can be inserted or updated"""
136
- if obj._objId is None:
137
- self.insert(obj)
138
- else:
139
- self.updateTo(obj)
140
-
141
- def selectById(self, objId):
142
- """Return the object which id is objId"""
143
- pass
144
-
145
- def exists(self, objId):
146
- """Return True if the id is in the database"""
147
- pass
148
-
149
- def selectAll(self, iterate=False):
150
- """Return all object from storage"""
151
- pass
152
-
153
- def selectFirst(self):
154
- """Return only the first element"""
155
- for obj in self.selectAll(iterate=True):
156
- return obj
157
- return None
158
-
159
- def selectBy(self, **args):
160
- """Select object meetings some criteria"""
161
- pass
162
-
163
- def selectByClass(self, className, includeSubclasses=True):
164
- """Select all object of a give class.
165
- By default object of subclasses will be retrieved also.
166
- This behaviour can be changed by passing includeSubclass=False"""
167
- return self.selectBy(classname=className)
168
-
169
- def getParent(self, obj):
170
- """ Retrieve the parent object of another. """
171
- pass
172
-
173
- def getFullName(self, obj):
174
- """ Return the full object name such as:
175
- grandparent.parent.objName
176
- """
177
- nameParts = []
178
- parent = obj
179
-
180
- while parent:
181
- nameParts.insert(0, parent.getLastName())
182
- parent = self.getParent(parent)
183
-
184
- return '.'.join(nameParts)
185
-
186
- def insertRelation(self, relName, creatorObj, parentObj, childObj):
187
- """ This function will add a new relation between two objects.
188
- Params:
189
- relName: the name of the relation to be added.
190
- creatorObj: this object will be the one who register the relation.
191
- parentObj: this is "parent" in the relation
192
- childObj: this is "child" in the relation
193
- """
194
- pass
195
-
196
- def getRelationChilds(self, relName, parentObj):
197
- """ Return all "child" objects for a given relation.
198
- Params:
199
- relName: the name of the relation.
200
- parentObj: this is "parent" in the relation
201
- Returns:
202
- a list of "child" objects.
203
- """
204
- pass
205
-
206
- def getRelationParents(self, relName, childObj):
207
- """ Return all "parent" objects for a given relation.
208
- Params:
209
- relName: the name of the relation.
210
- childObj: this is "child" in the relation
211
- Returns:
212
- a list of "parent" objects.
213
- """
214
- pass
215
-
216
- def getRelationsByCreator(self, creatorObj):
217
- """ Return all relations created by creatorObj. """
218
- pass
219
-
220
- def deleteRelations(self, creatorObj):
221
- """ Delete all relations created by object creatorObj """
222
- pass