itkdb-gtk 0.0.12__py3-none-any.whl → 0.0.16.dev0__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.
Potentially problematic release.
This version of itkdb-gtk might be problematic. Click here for more details.
- itkdb_gtk/ITkDBlogin.py +1 -0
- itkdb_gtk/ITkDButils.py +6 -2
- itkdb_gtk/__init__.py +9 -5
- itkdb_gtk/dashBoard.py +33 -9
- itkdb_gtk/dbGtkUtils.py +38 -0
- itkdb_gtk/{gndVITests.py → groundVITests.py} +32 -0
- itkdb_gtk/untrash_component.py +35 -0
- itkdb_gtk/uploadIVfiles.py +484 -0
- itkdb_gtk/uploadPetalInformation.py +1 -1
- itkdb_gtk/uploadTest.py +35 -10
- {itkdb_gtk-0.0.12.dist-info → itkdb_gtk-0.0.16.dev0.dist-info}/METADATA +10 -7
- itkdb_gtk-0.0.16.dev0.dist-info/RECORD +26 -0
- {itkdb_gtk-0.0.12.dist-info → itkdb_gtk-0.0.16.dev0.dist-info}/WHEEL +1 -1
- {itkdb_gtk-0.0.12.dist-info → itkdb_gtk-0.0.16.dev0.dist-info}/entry_points.txt +2 -1
- itkdb_gtk/checkComponent.py +0 -151
- itkdb_gtk/checkJSon.py +0 -56
- itkdb_gtk-0.0.12.dist-info/RECORD +0 -26
- {itkdb_gtk-0.0.12.dist-info → itkdb_gtk-0.0.16.dev0.dist-info}/top_level.txt +0 -0
itkdb_gtk/ITkDBlogin.py
CHANGED
itkdb_gtk/ITkDButils.py
CHANGED
|
@@ -235,9 +235,13 @@ def set_object_stage(client, SN, stage):
|
|
|
235
235
|
def get_DB_component(client, SN):
|
|
236
236
|
"""Get ta component by its serial number."""
|
|
237
237
|
global db_response
|
|
238
|
-
|
|
239
|
-
|
|
238
|
+
try:
|
|
239
|
+
db_response = client.get('getComponent', json={'component': SN})
|
|
240
|
+
return db_response
|
|
240
241
|
|
|
242
|
+
except Exception as e:
|
|
243
|
+
db_response = str(e)
|
|
244
|
+
return None
|
|
241
245
|
|
|
242
246
|
def upload_test(client, data, attachments=None):
|
|
243
247
|
"""Upload a test to the DB.
|
itkdb_gtk/__init__.py
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
__version__ = "0.0.12"
|
|
1
|
+
__version__ = "0.0.16.dev0"
|
|
4
2
|
|
|
5
3
|
|
|
6
4
|
def dash_board():
|
|
7
5
|
"""Launches the dash board."""
|
|
6
|
+
from .dashBoard import main
|
|
8
7
|
dashBoard.main()
|
|
9
8
|
|
|
10
9
|
|
|
@@ -20,9 +19,9 @@ def glueWeight():
|
|
|
20
19
|
main()
|
|
21
20
|
|
|
22
21
|
|
|
23
|
-
def
|
|
22
|
+
def groundVITests():
|
|
24
23
|
"""GND/VI tests."""
|
|
25
|
-
from .
|
|
24
|
+
from .groundVITests import main
|
|
26
25
|
main()
|
|
27
26
|
|
|
28
27
|
|
|
@@ -42,3 +41,8 @@ def uploadMultipleTests():
|
|
|
42
41
|
"""Upload multiple tests."""
|
|
43
42
|
from .uploadMultipleTests import main
|
|
44
43
|
main()
|
|
44
|
+
|
|
45
|
+
def uploadIVfiles():
|
|
46
|
+
"""Upload IV files of single and double modules"""
|
|
47
|
+
from .uploadIVfiles import main
|
|
48
|
+
main()
|
itkdb_gtk/dashBoard.py
CHANGED
|
@@ -5,14 +5,16 @@ import sys
|
|
|
5
5
|
try:
|
|
6
6
|
import dbGtkUtils
|
|
7
7
|
import getShipments
|
|
8
|
-
import
|
|
8
|
+
import groundVITests
|
|
9
9
|
import ITkDBlogin
|
|
10
10
|
import sendShipments
|
|
11
11
|
import uploadMultipleTests
|
|
12
12
|
import GlueWeight
|
|
13
|
+
import uploadIVfiles
|
|
13
14
|
|
|
14
15
|
except Exception:
|
|
15
|
-
from itkdb_gtk import dbGtkUtils, getShipments,
|
|
16
|
+
from itkdb_gtk import dbGtkUtils, getShipments, groundVITests, uploadIVfiles
|
|
17
|
+
from itkdb_gtk import ITkDBlogin, sendShipments, uploadMultipleTests, GlueWeight
|
|
16
18
|
|
|
17
19
|
import gi
|
|
18
20
|
|
|
@@ -22,7 +24,13 @@ from gi.repository import Gtk
|
|
|
22
24
|
|
|
23
25
|
class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
24
26
|
"""Dashboard class."""
|
|
25
|
-
|
|
27
|
+
UPLOAD_TEST = 1
|
|
28
|
+
CREATE_SHIPMNT = 2
|
|
29
|
+
RECV_SHIPMNT = 3
|
|
30
|
+
PETAL_GND = 4
|
|
31
|
+
GLUE_WEIGHT = 5
|
|
32
|
+
MOD_IV = 6
|
|
33
|
+
|
|
26
34
|
def __init__(self, session):
|
|
27
35
|
"""Initialization."""
|
|
28
36
|
super().__init__(title="ITkDB Dashboard", session=session)
|
|
@@ -59,6 +67,11 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
59
67
|
btnWeight.connect("clicked", self.glue_weight)
|
|
60
68
|
grid.attach(btnWeight, 0, irow, 1, 1)
|
|
61
69
|
|
|
70
|
+
btnModIV = Gtk.Button(label="Module IV")
|
|
71
|
+
btnModIV.connect("clicked", self.module_IV)
|
|
72
|
+
grid.attach(btnModIV, 1, irow, 1, 1)
|
|
73
|
+
|
|
74
|
+
|
|
62
75
|
irow += 1
|
|
63
76
|
grid.attach(Gtk.Label(), 0, irow, 1, 1)
|
|
64
77
|
|
|
@@ -83,7 +96,7 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
83
96
|
|
|
84
97
|
def upload_test(self, *args):
|
|
85
98
|
"""Launch upload test."""
|
|
86
|
-
bitn =
|
|
99
|
+
bitn = DashWindow.UPLOAD_TEST
|
|
87
100
|
bt = 1 << bitn
|
|
88
101
|
if self.mask & bt:
|
|
89
102
|
return
|
|
@@ -94,7 +107,7 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
94
107
|
|
|
95
108
|
def create_shipment(self, *args):
|
|
96
109
|
"""Launch sendShipment."""
|
|
97
|
-
bitn =
|
|
110
|
+
bitn = DashWindow.CREATE_SHIPMNT
|
|
98
111
|
bt = 1 << bitn
|
|
99
112
|
if self.mask & bt:
|
|
100
113
|
return
|
|
@@ -105,7 +118,7 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
105
118
|
|
|
106
119
|
def receive_shipment(self, *args):
|
|
107
120
|
"""Launch getShipments."""
|
|
108
|
-
bitn =
|
|
121
|
+
bitn = DashWindow.RECV_SHIPMNT
|
|
109
122
|
bt = 1 << bitn
|
|
110
123
|
if self.mask & bt:
|
|
111
124
|
return
|
|
@@ -116,18 +129,18 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
116
129
|
|
|
117
130
|
def petal_gnd(self, *args):
|
|
118
131
|
"""Petal GND/VI test."""
|
|
119
|
-
bitn =
|
|
132
|
+
bitn = DashWindow.PETAL_GND
|
|
120
133
|
bt = 1 << bitn
|
|
121
134
|
if self.mask & bt:
|
|
122
135
|
return
|
|
123
136
|
|
|
124
137
|
self.mask |= bt
|
|
125
|
-
W =
|
|
138
|
+
W = groundVITests.GroundingTest(self.session)
|
|
126
139
|
W.connect("destroy", self.app_closed, bitn)
|
|
127
140
|
|
|
128
141
|
def glue_weight(self, *args):
|
|
129
142
|
"""Glue Weight test."""
|
|
130
|
-
bitn =
|
|
143
|
+
bitn = DashWindow.GLUE_WEIGHT
|
|
131
144
|
bt = 1 << bitn
|
|
132
145
|
if self.mask & bt:
|
|
133
146
|
return
|
|
@@ -136,6 +149,17 @@ class DashWindow(dbGtkUtils.ITkDBWindow):
|
|
|
136
149
|
W = GlueWeight.GlueWeight(self.session)
|
|
137
150
|
W.connect("destroy", self.app_closed, bitn)
|
|
138
151
|
|
|
152
|
+
def module_IV(self, *args):
|
|
153
|
+
"""Module IV tests."""
|
|
154
|
+
bitn = DashWindow.MOD_IV
|
|
155
|
+
bt = 1 << bitn
|
|
156
|
+
if self.mask & bt:
|
|
157
|
+
return
|
|
158
|
+
|
|
159
|
+
self.mask |= bt
|
|
160
|
+
W = uploadIVfiles.IVwindow(self.session)
|
|
161
|
+
W.connect("destroy", self.app_closed, bitn)
|
|
162
|
+
|
|
139
163
|
def app_closed(self, *args):
|
|
140
164
|
"""Application window closed. Clear mask."""
|
|
141
165
|
bt = 1 << args[1]
|
itkdb_gtk/dbGtkUtils.py
CHANGED
|
@@ -7,11 +7,23 @@ from datetime import datetime
|
|
|
7
7
|
|
|
8
8
|
import dateutil.parser
|
|
9
9
|
import gi
|
|
10
|
+
import numpy as np
|
|
11
|
+
|
|
10
12
|
|
|
11
13
|
gi.require_version("Gtk", "3.0")
|
|
12
14
|
from gi.repository import Gtk, Gio, GLib
|
|
13
15
|
|
|
14
16
|
|
|
17
|
+
def is_a_date(txt):
|
|
18
|
+
"""check tha the input string is a date."""
|
|
19
|
+
try:
|
|
20
|
+
dateutil.parser.parse(txt, fuzzy=False)
|
|
21
|
+
return True
|
|
22
|
+
|
|
23
|
+
except Exception:
|
|
24
|
+
return False
|
|
25
|
+
|
|
26
|
+
|
|
15
27
|
def set_combo_iter(combo, txt, col=0):
|
|
16
28
|
"""Set scombo active iter to that containing txt in column col."""
|
|
17
29
|
model = combo.get_model()
|
|
@@ -55,6 +67,12 @@ class MyEncoder(json.JSONEncoder):
|
|
|
55
67
|
if isinstance(o, datetime):
|
|
56
68
|
text = o.astimezone().isoformat()
|
|
57
69
|
return text
|
|
70
|
+
elif isinstance(o, np.integer):
|
|
71
|
+
return int(o)
|
|
72
|
+
elif isinstance(o, np.floating):
|
|
73
|
+
return float(o)
|
|
74
|
+
elif isinstance(o, np.ndarray):
|
|
75
|
+
return o.tolist()
|
|
58
76
|
else:
|
|
59
77
|
return super().default(o)
|
|
60
78
|
|
|
@@ -300,6 +318,8 @@ def add_button_to_container(box, label, tooltip=None, callback=None):
|
|
|
300
318
|
btn.connect("clicked", callback)
|
|
301
319
|
|
|
302
320
|
box.pack_start(btn, True, False, 0)
|
|
321
|
+
|
|
322
|
+
return btn
|
|
303
323
|
|
|
304
324
|
|
|
305
325
|
class ITkDBWindow(Gtk.Window):
|
|
@@ -351,6 +371,9 @@ class ITkDBWindow(Gtk.Window):
|
|
|
351
371
|
|
|
352
372
|
# Create main content box
|
|
353
373
|
self.mainBox = Gtk.Box(orientation=Gtk.Orientation.VERTICAL)
|
|
374
|
+
self.mainBox.set_property("margin-left", 6)
|
|
375
|
+
self.mainBox.set_property("margin-right", 6)
|
|
376
|
+
|
|
354
377
|
self.add(self.mainBox)
|
|
355
378
|
|
|
356
379
|
# The text view and buffer
|
|
@@ -484,12 +507,18 @@ class DictDialog(Gtk.Grid):
|
|
|
484
507
|
super().__init__(column_spacing=5, row_spacing=1)
|
|
485
508
|
|
|
486
509
|
self.set_border_width(10)
|
|
510
|
+
self.factory = deepcopy(values)
|
|
487
511
|
self.values = deepcopy(values)
|
|
488
512
|
self.keys = {}
|
|
489
513
|
self.containers = {}
|
|
490
514
|
self.hidden_keys = hidden_keys
|
|
491
515
|
self.show_values()
|
|
492
516
|
|
|
517
|
+
def factory_reset(self):
|
|
518
|
+
"""Set values to original values."""
|
|
519
|
+
self.values = deepcopy(self.factory)
|
|
520
|
+
self.refresh()
|
|
521
|
+
|
|
493
522
|
def on_enter(self, entry, *args):
|
|
494
523
|
"""Get the value when we first enter into the Entry."""
|
|
495
524
|
self.keys[args[2]] = entry.get_text()
|
|
@@ -519,6 +548,15 @@ class DictDialog(Gtk.Grid):
|
|
|
519
548
|
elif isinstance(itm[last_key], datetime):
|
|
520
549
|
itm[last_key] = dateutil.parser.parse(txt)
|
|
521
550
|
|
|
551
|
+
elif is_a_date(itm[last_key]):
|
|
552
|
+
D = dateutil.parser.parse(txt)
|
|
553
|
+
out = D.isoformat(timespec='milliseconds')
|
|
554
|
+
if out[-1] not in ['zZ']:
|
|
555
|
+
out += 'Z'
|
|
556
|
+
|
|
557
|
+
itm[last_key] = out
|
|
558
|
+
self.containers[name].set_text(out)
|
|
559
|
+
|
|
522
560
|
else:
|
|
523
561
|
tp = type(itm[last_key])
|
|
524
562
|
itm[last_key] = tp(txt)
|
|
@@ -61,8 +61,16 @@ class GroundingTest(dbGtkUtils.ITkDBWindow):
|
|
|
61
61
|
grid.attach(lbl, 0, 0, 1, 1)
|
|
62
62
|
|
|
63
63
|
self.SN = Gtk.Entry()
|
|
64
|
+
self.SN.connect("focus-in-event", self.on_sn_enter)
|
|
65
|
+
self.SN.connect("focus-out-event", self.on_sn_leave)
|
|
64
66
|
grid.attach(self.SN, 1, 0, 1, 1)
|
|
65
67
|
|
|
68
|
+
self.alias = Gtk.Label(label="")
|
|
69
|
+
grid.attach(self.alias, 2, 0, 1, 1)
|
|
70
|
+
|
|
71
|
+
self.stage = Gtk.Label(label="")
|
|
72
|
+
grid.attach(self.stage, 3, 0, 1, 1)
|
|
73
|
+
|
|
66
74
|
lbl = Gtk.Label(label="Institute")
|
|
67
75
|
lbl.set_xalign(0)
|
|
68
76
|
grid.attach(lbl, 0, 1, 1, 1)
|
|
@@ -91,6 +99,7 @@ class GroundingTest(dbGtkUtils.ITkDBWindow):
|
|
|
91
99
|
# Create the Notebook pages
|
|
92
100
|
self.create_test_box("Visual Inspection", "VISUAL_INSPECTION")
|
|
93
101
|
self.create_test_box("Grounding", "GROUNDING_CHECK")
|
|
102
|
+
self.create_test_box("Pipe bending", "BENDING120")
|
|
94
103
|
|
|
95
104
|
# The text view
|
|
96
105
|
frame = self.create_text_view()
|
|
@@ -98,6 +107,29 @@ class GroundingTest(dbGtkUtils.ITkDBWindow):
|
|
|
98
107
|
|
|
99
108
|
self.show_all()
|
|
100
109
|
|
|
110
|
+
def on_sn_enter(self, entry, *args):
|
|
111
|
+
"""Enter in SN entry."""
|
|
112
|
+
self._sn = entry.get_text()
|
|
113
|
+
|
|
114
|
+
def on_sn_leave(self, entry, *args):
|
|
115
|
+
"""Leave SN entry."""
|
|
116
|
+
sn = entry.get_text()
|
|
117
|
+
if sn != self._sn:
|
|
118
|
+
self.query_db()
|
|
119
|
+
current_location = self.dbObject["currentLocation"]["code"]
|
|
120
|
+
dbGtkUtils.set_combo_iter(self.inst_cmb, current_location, 0)
|
|
121
|
+
|
|
122
|
+
stg = self.dbObject["currentStage"]["name"]
|
|
123
|
+
self.stage.set_text(stg)
|
|
124
|
+
|
|
125
|
+
alias = self.dbObject["alternativeIdentifier"]
|
|
126
|
+
self.alias.set_text(alias)
|
|
127
|
+
|
|
128
|
+
npages = self.notebook.get_n_pages()
|
|
129
|
+
for i in range(npages):
|
|
130
|
+
page = self.notebook.get_nth_page(i)
|
|
131
|
+
page.dict_dialog.factory_reset()
|
|
132
|
+
|
|
101
133
|
def create_test_box(self, label, test_name, institute="IFIC"):
|
|
102
134
|
"""Create and add to notebook a test dialog.
|
|
103
135
|
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""Un trash a trashed component."""
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
def untrash_component(client, SN, reason="Accidentally trashed"):
|
|
6
|
+
"""Un trash given component.
|
|
7
|
+
|
|
8
|
+
Args:
|
|
9
|
+
SN (str): Serial number of component to recover.
|
|
10
|
+
reason (str): message for the DB
|
|
11
|
+
Return:
|
|
12
|
+
dict: PDB response.
|
|
13
|
+
|
|
14
|
+
"""
|
|
15
|
+
DTO = {
|
|
16
|
+
'component': SN,
|
|
17
|
+
'trashed': False,
|
|
18
|
+
'reason': reason
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
response = client.post('setComponentTrashed', json=DTO)
|
|
22
|
+
return response
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
if __name__ == "__main__":
|
|
26
|
+
import sys
|
|
27
|
+
from itkdb_gtk import ITkDBlogin
|
|
28
|
+
dlg = ITkDBlogin.ITkDBlogin()
|
|
29
|
+
client = dlg.get_client()
|
|
30
|
+
|
|
31
|
+
try:
|
|
32
|
+
response = untrash_component(client, sys.argv[1])
|
|
33
|
+
|
|
34
|
+
except Exception as E:
|
|
35
|
+
print(str(E))
|
|
@@ -0,0 +1,484 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""Read IV files and create plots."""
|
|
3
|
+
import os
|
|
4
|
+
import json
|
|
5
|
+
import math
|
|
6
|
+
from pathlib import Path
|
|
7
|
+
|
|
8
|
+
import gi
|
|
9
|
+
import tempfile
|
|
10
|
+
|
|
11
|
+
gi.require_version("Gtk", "3.0")
|
|
12
|
+
from gi.repository import Gtk, Gio
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
from matplotlib.backends.backend_gtk3agg import FigureCanvasGTK3Agg as FigureCanvas
|
|
16
|
+
from matplotlib.backends.backend_gtk3 import NavigationToolbar2GTK3 as NavigationToolbar
|
|
17
|
+
import numpy as np
|
|
18
|
+
import matplotlib as mpl
|
|
19
|
+
import matplotlib.pyplot as plt
|
|
20
|
+
|
|
21
|
+
try:
|
|
22
|
+
import dbGtkUtils
|
|
23
|
+
import ITkDBlogin
|
|
24
|
+
import ITkDButils
|
|
25
|
+
import uploadTest
|
|
26
|
+
|
|
27
|
+
except ModuleNotFoundError:
|
|
28
|
+
from itkdb_gtk import dbGtkUtils, ITkDBlogin, ITkDButils, uploadTest
|
|
29
|
+
|
|
30
|
+
# Check if Gtk can be open
|
|
31
|
+
gtk_runs, gtk_args = Gtk.init_check()
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
def remove_files(W, flist):
|
|
35
|
+
for f in flist:
|
|
36
|
+
os.unlink(f)
|
|
37
|
+
|
|
38
|
+
def scale_iv(I, T1, T2):
|
|
39
|
+
"""Normalize corrent to given temperature (T2)
|
|
40
|
+
|
|
41
|
+
Args:
|
|
42
|
+
I (array): Current
|
|
43
|
+
T1 (float): Original temperature
|
|
44
|
+
T2 (float): New temperature.
|
|
45
|
+
|
|
46
|
+
Return:
|
|
47
|
+
Array with scaled currents.
|
|
48
|
+
|
|
49
|
+
"""
|
|
50
|
+
factor = (T2 / T1) ** 2 * math.exp((-1.2 / 8.62) * (1 / T2 - 1 / T1))
|
|
51
|
+
return factor * I
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
class IVwindow(dbGtkUtils.ITkDBWindow):
|
|
55
|
+
"""GUI for IV file handling."""
|
|
56
|
+
|
|
57
|
+
def __init__(self, session, title="IV window", options=None):
|
|
58
|
+
"""Initialization."""
|
|
59
|
+
super().__init__(
|
|
60
|
+
session=session, title=title, show_search=None, gtk_runs=gtk_runs
|
|
61
|
+
)
|
|
62
|
+
self.mdata = {}
|
|
63
|
+
self.mod_type = {}
|
|
64
|
+
self.mod_SN = {}
|
|
65
|
+
self.difference = None
|
|
66
|
+
self.canvas = None
|
|
67
|
+
|
|
68
|
+
self.init_window()
|
|
69
|
+
|
|
70
|
+
def init_window(self):
|
|
71
|
+
"""Prepare the Gtk window."""
|
|
72
|
+
self.hb.props.title = "IV data"
|
|
73
|
+
|
|
74
|
+
button = Gtk.Button()
|
|
75
|
+
icon = Gio.ThemedIcon(name="view-refresh-symbolic")
|
|
76
|
+
image = Gtk.Image.new_from_gicon(icon, Gtk.IconSize.BUTTON)
|
|
77
|
+
button.add(image)
|
|
78
|
+
button.set_tooltip_text("Click to refresh canvas.")
|
|
79
|
+
button.connect("clicked", self.on_refresh)
|
|
80
|
+
self.hb.pack_end(button)
|
|
81
|
+
|
|
82
|
+
# Button to upload
|
|
83
|
+
button = Gtk.Button()
|
|
84
|
+
icon = Gio.ThemedIcon(name="document-send-symbolic")
|
|
85
|
+
image = Gtk.Image.new_from_gicon(icon, Gtk.IconSize.BUTTON)
|
|
86
|
+
button.add(image)
|
|
87
|
+
button.set_tooltip_text("Click to upload test")
|
|
88
|
+
button.connect("clicked", self.upload_test)
|
|
89
|
+
self.hb.pack_end(button)
|
|
90
|
+
|
|
91
|
+
# File entry and search button
|
|
92
|
+
self.single_file = Gtk.FileChooserButton()
|
|
93
|
+
self.single_file.connect("file-set", self.on_single_file_set)
|
|
94
|
+
|
|
95
|
+
self.double_file = Gtk.FileChooserButton()
|
|
96
|
+
self.double_file.connect("file-set", self.on_double_file_set)
|
|
97
|
+
|
|
98
|
+
self.single_SN = Gtk.Label(label="(None)")
|
|
99
|
+
self.double_SN = Gtk.Label(label="(None)")
|
|
100
|
+
|
|
101
|
+
grid = Gtk.Grid(column_spacing=5, row_spacing=1)
|
|
102
|
+
|
|
103
|
+
grid.attach(Gtk.Label(label="Files"), 1, 0, 1, 1)
|
|
104
|
+
grid.attach(Gtk.Label(label="Serial No."), 2, 0, 1, 1)
|
|
105
|
+
|
|
106
|
+
grid.attach(Gtk.Label(label="Single Data File"), 0, 1, 1, 1)
|
|
107
|
+
grid.attach(self.single_file, 1, 1, 1, 1)
|
|
108
|
+
grid.attach(self.single_SN, 2, 1, 1, 1)
|
|
109
|
+
|
|
110
|
+
grid.attach(Gtk.Label(label="Double Data File"), 0, 2, 1, 1)
|
|
111
|
+
grid.attach(self.double_file, 1, 2, 1, 1)
|
|
112
|
+
grid.attach(self.double_SN, 2, 2, 1, 1)
|
|
113
|
+
|
|
114
|
+
btn = Gtk.Button(label="Compute difference")
|
|
115
|
+
btn.connect("clicked", self.on_difference)
|
|
116
|
+
grid.attach(btn, 1, 3, 1, 1)
|
|
117
|
+
|
|
118
|
+
self.mainBox.pack_start(grid, False, True, 0)
|
|
119
|
+
|
|
120
|
+
self.fig = mpl.figure.Figure()
|
|
121
|
+
self.fig.tight_layout()
|
|
122
|
+
sw = Gtk.ScrolledWindow() # Gtk.Box(orientation=Gtk.Orientation.VERTICAL)
|
|
123
|
+
|
|
124
|
+
# A scrolled window border goes outside the scrollbars and viewport
|
|
125
|
+
sw.set_border_width(10)
|
|
126
|
+
sw.set_size_request(310, 310)
|
|
127
|
+
|
|
128
|
+
self.canvas = FigureCanvas(self.fig) # a Gtk.DrawingArea
|
|
129
|
+
self.canvas.set_size_request(400, 300)
|
|
130
|
+
sw.add(self.canvas)
|
|
131
|
+
self.mainBox.pack_start(sw, True, True, 0)
|
|
132
|
+
|
|
133
|
+
# Create toolbar
|
|
134
|
+
toolbar = NavigationToolbar(self.canvas)
|
|
135
|
+
self.mainBox.pack_start(toolbar, False, False, 0)
|
|
136
|
+
|
|
137
|
+
# The text view
|
|
138
|
+
frame = self.create_text_view()
|
|
139
|
+
self.mainBox.pack_start(frame, True, True, 5)
|
|
140
|
+
|
|
141
|
+
self.show_all()
|
|
142
|
+
|
|
143
|
+
def upload_test(self, *args):
|
|
144
|
+
"""Upload available tests."""
|
|
145
|
+
test = ITkDButils.get_test_skeleton(
|
|
146
|
+
self.session, "MODULE", self.mdata["double"]["TestType"]
|
|
147
|
+
)
|
|
148
|
+
mdata = self.mdata["double"]
|
|
149
|
+
V = mdata["curve"]["V"]
|
|
150
|
+
I = np.abs(mdata["curve"]["I"])
|
|
151
|
+
|
|
152
|
+
indx = np.where(V == 500)[0]
|
|
153
|
+
i_500 = I[indx][0]
|
|
154
|
+
|
|
155
|
+
indx = np.where(V == 700)
|
|
156
|
+
rms = np.std(I[indx])
|
|
157
|
+
|
|
158
|
+
test["component"] = self.mod_SN["double"]
|
|
159
|
+
test["institution"] = mdata["Institute"]
|
|
160
|
+
test["runNumber"] = mdata["RunNumber"]
|
|
161
|
+
test["date"] = ITkDButils.get_db_date(
|
|
162
|
+
"{} {}".format(mdata["Date"], mdata["Time"])
|
|
163
|
+
)
|
|
164
|
+
test["passed"] = True
|
|
165
|
+
test["problems"] = False
|
|
166
|
+
test["properties"]["VBIAS_SMU"] = mdata["Vbias_SMU"]
|
|
167
|
+
test["properties"]["RSERIES"] = mdata["Rseries"]
|
|
168
|
+
test["properties"]["TEST_DMM"] = mdata["Test_DMM"]
|
|
169
|
+
test["properties"]["RSHUNT"] = mdata["Rshunt"]
|
|
170
|
+
test["properties"]["RUNNUMBER"] = mdata["RunNumber"]
|
|
171
|
+
test["properties"]["COMMENTS"] = mdata["Comments"]
|
|
172
|
+
test["properties"]["ALGORITHM_VERSION"] = "0.0.0"
|
|
173
|
+
test["properties"]["SOFTWARE_TYPE_VERSION"] = "pyProbe"
|
|
174
|
+
test["properties"]["MODULE_STAGE"] = mdata["Module_Stage"]
|
|
175
|
+
test["results"]["TEMPERATURE"] = mdata["Temperature"]
|
|
176
|
+
test["results"]["HUMIDITY"] = mdata["Humidity"]
|
|
177
|
+
test["results"]["VBD"] = mdata["curve"]["V"][-1]
|
|
178
|
+
test["results"]["I_500V"] = i_500
|
|
179
|
+
test["results"]["VOLTAGE"] = V
|
|
180
|
+
test["results"]["CURRENT"] = I
|
|
181
|
+
test["results"]["RMS_STABILITY"] = 0.0
|
|
182
|
+
test["results"]["SHUNT_VOLTAGE"] = np.zeros(V.shape)
|
|
183
|
+
|
|
184
|
+
# write attachment.
|
|
185
|
+
items = [
|
|
186
|
+
"Type",
|
|
187
|
+
"Wafer",
|
|
188
|
+
"Module_SN",
|
|
189
|
+
"Module_Stage",
|
|
190
|
+
"Date",
|
|
191
|
+
"Time",
|
|
192
|
+
"Institute",
|
|
193
|
+
"TestType",
|
|
194
|
+
"Vbias_SMU",
|
|
195
|
+
"Rseries",
|
|
196
|
+
"Test_DMM",
|
|
197
|
+
"Rshunt",
|
|
198
|
+
"Software type and version, fw version",
|
|
199
|
+
"RunNumber",
|
|
200
|
+
"Temperature",
|
|
201
|
+
"Humidity",
|
|
202
|
+
"Comments",
|
|
203
|
+
]
|
|
204
|
+
fnam = "{}_{}_IV_{}-".format(self.mod_SN["double"], mdata["Module_Stage"], mdata["RunNumber"])
|
|
205
|
+
data_out = tempfile.NamedTemporaryFile('w', prefix=fnam, suffix=".dat", delete=False)
|
|
206
|
+
data_out.write("{}\n".format(fnam))
|
|
207
|
+
for key in items:
|
|
208
|
+
if key == "Module_SN":
|
|
209
|
+
data_out.write("{}: {}\n".format(key, self.mod_SN["double"]))
|
|
210
|
+
else:
|
|
211
|
+
data_out.write("{}: {}\n".format(key, mdata[key]))
|
|
212
|
+
|
|
213
|
+
for il, label in enumerate(mdata["curve"]["labels"]):
|
|
214
|
+
if il:
|
|
215
|
+
data_out.write('\t')
|
|
216
|
+
data_out.write(label)
|
|
217
|
+
data_out.write("\n")
|
|
218
|
+
|
|
219
|
+
ndata = len(mdata["curve"]["V"])
|
|
220
|
+
for i in range(ndata):
|
|
221
|
+
data_out.write("{:.2f}\t{:.2f}\t{:.2f}\n".format(V[i], self.difference[i], 0.0))
|
|
222
|
+
|
|
223
|
+
print(data_out.name)
|
|
224
|
+
data_out.close()
|
|
225
|
+
|
|
226
|
+
js_out = tempfile.NamedTemporaryFile('w', prefix="payload-", suffix=".json", delete=False)
|
|
227
|
+
js_out.write(json.dumps(test, indent=3, cls=dbGtkUtils.MyEncoder))
|
|
228
|
+
js_out.close()
|
|
229
|
+
|
|
230
|
+
attachment = ITkDButils.Attachment(data_out.name, "resultsFile", fnam)
|
|
231
|
+
uploadW = uploadTest.UploadTest(self.session, js_out.name, attachment)
|
|
232
|
+
uploadW.connect("destroy", remove_files, [data_out.name, js_out.name])
|
|
233
|
+
|
|
234
|
+
def on_refresh(self, *args):
|
|
235
|
+
"""Refresh canvas."""
|
|
236
|
+
if self.fig and self.canvas:
|
|
237
|
+
self.fig.tight_layout()
|
|
238
|
+
self.canvas.draw()
|
|
239
|
+
|
|
240
|
+
def find_module(self, SN):
|
|
241
|
+
"""Find module (SN) on database
|
|
242
|
+
|
|
243
|
+
Args:
|
|
244
|
+
----
|
|
245
|
+
SN (str): Module Serial number
|
|
246
|
+
"""
|
|
247
|
+
md = ITkDButils.get_DB_component(self.session, SN)
|
|
248
|
+
if md is None:
|
|
249
|
+
dbGtkUtils.complain(
|
|
250
|
+
"Could not find {}".format(SN), str(ITkDButils.get_db_response())
|
|
251
|
+
)
|
|
252
|
+
|
|
253
|
+
return md
|
|
254
|
+
|
|
255
|
+
def on_single_file_set(self, *args):
|
|
256
|
+
"""File chosen."""
|
|
257
|
+
fnam = self.single_file.get_filename()
|
|
258
|
+
if fnam is None or not Path(fnam).exists():
|
|
259
|
+
dbGtkUtils.complain("Could not find data file", fnam, parent=self)
|
|
260
|
+
|
|
261
|
+
mdata = self.read_file(fnam)
|
|
262
|
+
|
|
263
|
+
SN = mdata["Module_SN"]
|
|
264
|
+
self.write_message("Reading data for module {}\n".format(SN))
|
|
265
|
+
md = self.find_module(SN)
|
|
266
|
+
if md is None:
|
|
267
|
+
self.write_message("...object does not exist.\n")
|
|
268
|
+
self.single_file.unselect_all()
|
|
269
|
+
return
|
|
270
|
+
|
|
271
|
+
# All good
|
|
272
|
+
self.mod_SN["single"] = SN
|
|
273
|
+
self.mdata["single"] = mdata
|
|
274
|
+
self.mod_type["single"] = md["type"]["code"]
|
|
275
|
+
print(self.mod_type["single"])
|
|
276
|
+
|
|
277
|
+
self.single_SN.set_text("{} - {}".format(SN, md["type"]["name"]))
|
|
278
|
+
self.show_curve(
|
|
279
|
+
131,
|
|
280
|
+
mdata["curve"]["V"],
|
|
281
|
+
mdata["curve"]["I"],
|
|
282
|
+
self.mod_type["single"][0:4],
|
|
283
|
+
mdata["curve"]["labels"][0],
|
|
284
|
+
mdata["curve"]["labels"][1],
|
|
285
|
+
)
|
|
286
|
+
|
|
287
|
+
def on_double_file_set(self, *args):
|
|
288
|
+
"File chosen for the 'double module'"
|
|
289
|
+
fnam = self.double_file.get_filename()
|
|
290
|
+
if fnam is None or not Path(fnam).exists():
|
|
291
|
+
dbGtkUtils.complain("Could not find data file", fnam, parent=self)
|
|
292
|
+
|
|
293
|
+
mdata = self.read_file(fnam)
|
|
294
|
+
|
|
295
|
+
# Check SN in data file
|
|
296
|
+
SN = mdata["Module_SN"]
|
|
297
|
+
halfM_SN = SN
|
|
298
|
+
if "single" in self.mod_SN:
|
|
299
|
+
if self.mod_SN["single"] == SN:
|
|
300
|
+
dbGtkUtils.complain("Wrong module SN", "{} already used.".format(SN))
|
|
301
|
+
self.double_file.unselect_all()
|
|
302
|
+
return
|
|
303
|
+
|
|
304
|
+
# Check that it exists in the DB
|
|
305
|
+
self.write_message("Reading data for module {}\n".format(SN))
|
|
306
|
+
md = self.find_module(SN)
|
|
307
|
+
if md is None:
|
|
308
|
+
self.write_message("...object does not exist.\n")
|
|
309
|
+
self.double_file.unselect_all()
|
|
310
|
+
return
|
|
311
|
+
|
|
312
|
+
found_child = False
|
|
313
|
+
if md["type"]["name"].find("Ring"):
|
|
314
|
+
self.write_message("...This is a Ring module. Searching children in DB\n")
|
|
315
|
+
for child in md["children"]:
|
|
316
|
+
if child["component"]:
|
|
317
|
+
ctype = child["type"]["code"]
|
|
318
|
+
if ctype.find("MODULE")<0:
|
|
319
|
+
continue
|
|
320
|
+
|
|
321
|
+
cSN = child["component"]["serialNumber"]
|
|
322
|
+
if cSN == self.mod_SN["single"]:
|
|
323
|
+
continue
|
|
324
|
+
|
|
325
|
+
halfM_SN = cSN
|
|
326
|
+
found_child = True
|
|
327
|
+
self.write_message("...found {}\n".format(halfM_SN))
|
|
328
|
+
break
|
|
329
|
+
|
|
330
|
+
|
|
331
|
+
if not found_child:
|
|
332
|
+
self.write_message("Requesting a Half Module SN\n")
|
|
333
|
+
halfM_SN = dbGtkUtils.get_a_value("Give Half Module SN", "Serial Number")
|
|
334
|
+
|
|
335
|
+
md = ITkDButils.get_DB_component(self.session, halfM_SN)
|
|
336
|
+
if md is None:
|
|
337
|
+
dbGtkUtils.complain(
|
|
338
|
+
"Could not find {}".format(halfM_SN),
|
|
339
|
+
str(ITkDButils.get_db_response()),
|
|
340
|
+
)
|
|
341
|
+
self.double_file.unselect_all()
|
|
342
|
+
return
|
|
343
|
+
|
|
344
|
+
self.write_message("... {}".format(halfM_SN))
|
|
345
|
+
|
|
346
|
+
if "single" in self.mod_type:
|
|
347
|
+
if self.mod_type["single"] == md["type"]["code"]:
|
|
348
|
+
dbGtkUtils.complain(
|
|
349
|
+
"Wrong module type.",
|
|
350
|
+
"Module type cannot be {}".format(self.mod_type["single"]),
|
|
351
|
+
)
|
|
352
|
+
|
|
353
|
+
self.double_file.unselect_all()
|
|
354
|
+
return
|
|
355
|
+
|
|
356
|
+
self.mod_SN["double"] = halfM_SN
|
|
357
|
+
self.mod_type["double"] = md["type"]["code"]
|
|
358
|
+
self.mdata["double"] = mdata
|
|
359
|
+
|
|
360
|
+
self.double_SN.set_text("{} - {}".format(SN, md["type"]["name"]))
|
|
361
|
+
self.show_curve(
|
|
362
|
+
133,
|
|
363
|
+
mdata["curve"]["V"],
|
|
364
|
+
mdata["curve"]["I"],
|
|
365
|
+
"Double",
|
|
366
|
+
mdata["curve"]["labels"][0],
|
|
367
|
+
None,
|
|
368
|
+
)
|
|
369
|
+
|
|
370
|
+
# Compute difference if single already available
|
|
371
|
+
if "single" in self.mdata:
|
|
372
|
+
self.on_difference()
|
|
373
|
+
|
|
374
|
+
def on_difference(self, *args):
|
|
375
|
+
"""Compute difference."""
|
|
376
|
+
if "single" not in self.mdata or "double" not in self.mdata:
|
|
377
|
+
dbGtkUtils.complain(
|
|
378
|
+
"Data needed", "Check if single oand doubel module data are available"
|
|
379
|
+
)
|
|
380
|
+
return
|
|
381
|
+
|
|
382
|
+
single_I = scale_iv(
|
|
383
|
+
self.mdata["single"]["curve"]["I"],
|
|
384
|
+
self.mdata["single"]["Temperature"] + 273.0,
|
|
385
|
+
self.mdata["double"]["Temperature"] + 273.0,
|
|
386
|
+
)
|
|
387
|
+
|
|
388
|
+
self.difference = self.mdata["double"]["curve"]["I"] - single_I
|
|
389
|
+
|
|
390
|
+
self.show_curve(
|
|
391
|
+
132,
|
|
392
|
+
self.mdata["double"]["curve"]["V"],
|
|
393
|
+
self.difference,
|
|
394
|
+
self.mod_type["double"][0:4],
|
|
395
|
+
self.mdata["double"]["curve"]["labels"][0],
|
|
396
|
+
None,
|
|
397
|
+
)
|
|
398
|
+
|
|
399
|
+
def show_curve(self, subplot, X, Y, title=None, xlabel="X", ylabel="Y"):
|
|
400
|
+
"""Shows data"""
|
|
401
|
+
ax = self.fig.add_subplot(subplot)
|
|
402
|
+
if xlabel:
|
|
403
|
+
ax.set_xlabel(xlabel)
|
|
404
|
+
|
|
405
|
+
if ylabel:
|
|
406
|
+
ax.set_ylabel(ylabel)
|
|
407
|
+
|
|
408
|
+
if title:
|
|
409
|
+
ax.set_title(title)
|
|
410
|
+
|
|
411
|
+
ax.plot(X, Y)
|
|
412
|
+
ax.grid()
|
|
413
|
+
self.on_refresh()
|
|
414
|
+
|
|
415
|
+
@staticmethod
|
|
416
|
+
def read_file(fnam):
|
|
417
|
+
"""Read a data file. Return dictionary with all teh data."""
|
|
418
|
+
labels = []
|
|
419
|
+
metadata = {}
|
|
420
|
+
with open(fnam, "r", encoding="utf-8") as ifile:
|
|
421
|
+
first = True
|
|
422
|
+
for line in ifile:
|
|
423
|
+
if first:
|
|
424
|
+
first = False
|
|
425
|
+
ipos = line.rfind('.')
|
|
426
|
+
metadata["fname"] = line[:ipos]
|
|
427
|
+
continue
|
|
428
|
+
|
|
429
|
+
if line.find("Voltage [V]") >= 0:
|
|
430
|
+
labels = line.split("\t")
|
|
431
|
+
break
|
|
432
|
+
|
|
433
|
+
rc = line.find(":")
|
|
434
|
+
if rc >= 0:
|
|
435
|
+
key = line[:rc].strip()
|
|
436
|
+
val = line[rc + 1 :].strip()
|
|
437
|
+
if key in ["Temperature", "Humidity"]:
|
|
438
|
+
metadata[key] = float(val)
|
|
439
|
+
else:
|
|
440
|
+
metadata[key] = val
|
|
441
|
+
|
|
442
|
+
V = []
|
|
443
|
+
I = []
|
|
444
|
+
for line in ifile:
|
|
445
|
+
data = [float(s) for s in line.split()]
|
|
446
|
+
V.append(data[0])
|
|
447
|
+
I.append(data[1])
|
|
448
|
+
|
|
449
|
+
metadata["curve"] = {
|
|
450
|
+
"V": np.array(V),
|
|
451
|
+
"I": np.array(I),
|
|
452
|
+
"labels": labels[0:2],
|
|
453
|
+
}
|
|
454
|
+
return metadata
|
|
455
|
+
|
|
456
|
+
|
|
457
|
+
if __name__ == "__main__":
|
|
458
|
+
import sys
|
|
459
|
+
|
|
460
|
+
# DB login
|
|
461
|
+
dlg = ITkDBlogin.ITkDBlogin()
|
|
462
|
+
client = dlg.get_client()
|
|
463
|
+
if client is None:
|
|
464
|
+
print("Could not connect to DB with provided credentials.")
|
|
465
|
+
dlg.die()
|
|
466
|
+
sys.exit()
|
|
467
|
+
|
|
468
|
+
client.user_gui = dlg
|
|
469
|
+
|
|
470
|
+
# Start the Application
|
|
471
|
+
win = IVwindow(client)
|
|
472
|
+
win.show_all()
|
|
473
|
+
win.set_accept_focus(True)
|
|
474
|
+
win.present()
|
|
475
|
+
win.connect("destroy", Gtk.main_quit)
|
|
476
|
+
|
|
477
|
+
try:
|
|
478
|
+
Gtk.main()
|
|
479
|
+
except KeyboardInterrupt:
|
|
480
|
+
print("Arrggggg !!!")
|
|
481
|
+
|
|
482
|
+
dlg.die()
|
|
483
|
+
print("Bye !!")
|
|
484
|
+
sys.exit()
|
itkdb_gtk/uploadTest.py
CHANGED
|
@@ -88,7 +88,7 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
88
88
|
----
|
|
89
89
|
session: ITkDB session
|
|
90
90
|
payload: path of test file
|
|
91
|
-
attachment: an Attachment object.
|
|
91
|
+
attachment: an Attachment object or list of attachments.
|
|
92
92
|
|
|
93
93
|
"""
|
|
94
94
|
self.payload = payload
|
|
@@ -101,7 +101,12 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
101
101
|
if attachment.path is not None:
|
|
102
102
|
self.attachments.append(attachment)
|
|
103
103
|
else:
|
|
104
|
-
|
|
104
|
+
try:
|
|
105
|
+
for att in attachment:
|
|
106
|
+
self.attachments.append(att)
|
|
107
|
+
|
|
108
|
+
except TypeError:
|
|
109
|
+
print("Wrong attachment: {}".format(attachment))
|
|
105
110
|
|
|
106
111
|
global gtk_runs
|
|
107
112
|
if gtk_runs:
|
|
@@ -168,15 +173,15 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
168
173
|
# The "Add attachment" button.
|
|
169
174
|
box = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL)
|
|
170
175
|
self.mainBox.pack_start(box, False, False, 0)
|
|
171
|
-
dbGtkUtils.add_button_to_container(box, "Attachments",
|
|
176
|
+
self.btn_attch = dbGtkUtils.add_button_to_container(box, "Attachments",
|
|
172
177
|
"Click to edit attachments.",
|
|
173
178
|
self.edit_attachments)
|
|
174
179
|
|
|
175
|
-
dbGtkUtils.add_button_to_container(box, "Comments",
|
|
180
|
+
self.btn_comments = dbGtkUtils.add_button_to_container(box, "Comments",
|
|
176
181
|
"Click to edit comments.",
|
|
177
182
|
self.edit_comments)
|
|
178
183
|
|
|
179
|
-
dbGtkUtils.add_button_to_container(box, "Defects",
|
|
184
|
+
self.btn_defects = dbGtkUtils.add_button_to_container(box, "Defects",
|
|
180
185
|
"Click to edit defects.",
|
|
181
186
|
self.edit_defects)
|
|
182
187
|
|
|
@@ -200,11 +205,21 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
200
205
|
else:
|
|
201
206
|
print("Input file does not exists: {}".format(self.payload))
|
|
202
207
|
|
|
203
|
-
if len(self.attachments):
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
+
#if len(self.attachments):
|
|
209
|
+
# dC = [A for A in self.attachments]
|
|
210
|
+
# self.attachments.clear()
|
|
211
|
+
# for A in dC:
|
|
212
|
+
# self.append_attachment_to_view(A)
|
|
213
|
+
|
|
214
|
+
if len(self.attachments) > 0:
|
|
215
|
+
self.btn_attch.set_label("Attachments ({})".format(len(self.attachments)))
|
|
216
|
+
|
|
217
|
+
if len(self.comments) > 0:
|
|
218
|
+
self.btn_comments.set_label("Comments ({})".format(len(self.comments)))
|
|
219
|
+
|
|
220
|
+
if len(self.defects) > 0:
|
|
221
|
+
self.btn_defects.set_label("Defects ({})".format(len(self.defects)))
|
|
222
|
+
|
|
208
223
|
|
|
209
224
|
def get_test_institute(self):
|
|
210
225
|
"""Select an institue."""
|
|
@@ -286,6 +301,10 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
286
301
|
SA.hide()
|
|
287
302
|
SA.destroy()
|
|
288
303
|
|
|
304
|
+
if len(self.attachments) > 0:
|
|
305
|
+
self.btn_attch.set_label("Attachments ({})".format(len(self.attachments)))
|
|
306
|
+
|
|
307
|
+
|
|
289
308
|
def edit_comments(self, *args):
|
|
290
309
|
"""Edit test comments."""
|
|
291
310
|
SC = ShowComments("Test Comments", self.comments, self)
|
|
@@ -296,6 +315,9 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
296
315
|
SC.hide()
|
|
297
316
|
SC.destroy()
|
|
298
317
|
|
|
318
|
+
if len(self.comments) > 0:
|
|
319
|
+
self.btn_comments.set_label("Comments ({})".format(len(self.comments)))
|
|
320
|
+
|
|
299
321
|
def edit_defects(self, *args):
|
|
300
322
|
"""Edit test defects."""
|
|
301
323
|
SD = ShowDefects("Test Defects", self.defects, self)
|
|
@@ -306,6 +328,9 @@ class UploadTest(dbGtkUtils.ITkDBWindow):
|
|
|
306
328
|
SD.hide()
|
|
307
329
|
SD.destroy()
|
|
308
330
|
|
|
331
|
+
if len(self.defects) > 0:
|
|
332
|
+
self.btn_defects.set_label("Defects ({})".format(len(self.defects)))
|
|
333
|
+
|
|
309
334
|
def upload_test_gui(self, *args):
|
|
310
335
|
"""Uploads test and attachments."""
|
|
311
336
|
self.upload_test()
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
|
-
Name:
|
|
3
|
-
Version: 0.0.
|
|
2
|
+
Name: itkdb_gtk
|
|
3
|
+
Version: 0.0.16.dev0
|
|
4
4
|
Summary: A collection of Gtk based GUI to access ITkDB.
|
|
5
5
|
Author-email: Carlos Lacasta <carlos.lacasta@cern.ch>
|
|
6
6
|
Project-URL: Homepage, https://gitlab.cern.ch/atlas-itk/sw/db/itk-pdb-gtk-gui-utils
|
|
@@ -9,7 +9,7 @@ Classifier: Programming Language :: Python :: 3
|
|
|
9
9
|
Classifier: Operating System :: OS Independent
|
|
10
10
|
Requires-Python: >=3.7
|
|
11
11
|
Description-Content-Type: text/markdown
|
|
12
|
-
Requires-Dist: itkdb
|
|
12
|
+
Requires-Dist: itkdb >=0.4.0
|
|
13
13
|
Requires-Dist: openpyxl
|
|
14
14
|
Requires-Dist: pyserial
|
|
15
15
|
Requires-Dist: python-dateutil
|
|
@@ -58,12 +58,15 @@ reception. It will finally make the DB aware of the items receptioned.
|
|
|
58
58
|
Create a new shipment. Allows to add items with the QR reader as well as from a
|
|
59
59
|
GUI dialog. One can add comments and attachments to the shipment.
|
|
60
60
|
|
|
61
|
-
##
|
|
62
|
-
Allows to enter valueos, comments and defects for those
|
|
61
|
+
## groundVITests.py
|
|
62
|
+
Allows to upload and enter valueos, comments and defects for those items in the gounding
|
|
63
63
|
and visual instpections tests of the petal core.
|
|
64
64
|
|
|
65
|
+
## uploadIVfiles.py
|
|
66
|
+
The idea behind this is that we messure the IV on a Ring module and on only one of the to Half modules. The IV of the remaining half modules is derived from the other 2. Eventually the IV test can be uploaded to the DB.
|
|
67
|
+
|
|
65
68
|
## dashBoard.py
|
|
66
69
|
This is an launcher application from which we can start most of the other
|
|
67
70
|
applications. It is a very good starting point. There is a Gnome desktop file (ITkDB.desktop)
|
|
68
|
-
that needs to be copied to
|
|
69
|
-
needs to go to
|
|
71
|
+
that needs to be copied to `$HOME/.local/share/applications` and an icon (ITkDB.svg) that
|
|
72
|
+
needs to go to `$HOME/.local/share/icons`
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
itkdb_gtk/GlueWeight.py,sha256=1Ssu6m_KL1PAHHI76yn9bnqSLSqxbc--S-DtV2V1L4g,12294
|
|
2
|
+
itkdb_gtk/ITkDB.desktop,sha256=v_K4mHsDxb912J1XGo6mOlbW2TkHvYNGrKmiOnsBQqM,172
|
|
3
|
+
itkdb_gtk/ITkDB.svg,sha256=Rb1DyhhGj504-h3vi-H6BF_Gm-OUciIXWOmzZbjGns4,23991
|
|
4
|
+
itkdb_gtk/ITkDBlogin.py,sha256=lYuTz8FghvqUYRpua9lGaE_dJk_AOmzZhBk2VZH5bKc,9929
|
|
5
|
+
itkdb_gtk/ITkDButils.py,sha256=I88VFnJMdcdWpu2c3VKoGlhMzh3LkfWuZxkSCoXaJh0,14943
|
|
6
|
+
itkdb_gtk/ShowAttachments.py,sha256=yHa3W1_KtDEGBEcLjGsCONKDP0ntDJNggi3T1bc48Yg,4693
|
|
7
|
+
itkdb_gtk/ShowComments.py,sha256=Poyx3bljWEMwhB2FDvBVMSRPcqv9aowlDtbbcs8JgYw,2989
|
|
8
|
+
itkdb_gtk/ShowDefects.py,sha256=hnXZKfGshoTBJindbjrNgO6kKpVXwKO8Cu6Txn4cCXE,3329
|
|
9
|
+
itkdb_gtk/__init__.py,sha256=IzKUTrs_YUOMXDwJis6-LVPNcK02n6CjtcIJIcPcLZQ,828
|
|
10
|
+
itkdb_gtk/dashBoard.py,sha256=niEjM5pNgNL8jS5jf09GsxRDjKVLshTiMU19oTJfhYs,5146
|
|
11
|
+
itkdb_gtk/dbGtkUtils.py,sha256=w9zj8ky2jOKtVsm8p9mhbox6_zzBTItcFQJI1RBVAgo,21750
|
|
12
|
+
itkdb_gtk/getShipments.py,sha256=6xNTFAQ1Xon8M20U5BSRJkRc4P7vfNuG4liktoMTaa0,18718
|
|
13
|
+
itkdb_gtk/groundVITests.py,sha256=t_UvPDplEbbvEDKZzLxib6aQV-bhg-7mVAyEdcGtmfM,9193
|
|
14
|
+
itkdb_gtk/readAVSdata.py,sha256=VCoCece2tuhbd7yfaCCTXuRbGEFUUV2gCcJozQYhPRE,19379
|
|
15
|
+
itkdb_gtk/readGoogleSheet.py,sha256=cQ_pVsS_nwUh0bnXl7AP4in9kQ3Q-p8BIvXvvrTRInc,2679
|
|
16
|
+
itkdb_gtk/sendShipments.py,sha256=yaKQ30fMG7bt3Zk7Rkgmla04nqfboA8zg3a-rleG9-g,13133
|
|
17
|
+
itkdb_gtk/untrash_component.py,sha256=fZWanuPww1RLJ-Fduso4EqfLlcBsd5ryJymr1xJZEUM,756
|
|
18
|
+
itkdb_gtk/uploadIVfiles.py,sha256=JggY03qE2SsVvR7MKW-fu9-l6RgYIfM0mH7yBBCjjMI,15521
|
|
19
|
+
itkdb_gtk/uploadMultipleTests.py,sha256=anbn9_2AGmgfcNZozIowEvpBG---K36Kihx_M2j4J50,19892
|
|
20
|
+
itkdb_gtk/uploadPetalInformation.py,sha256=4d4eP6-iDI0Vygry4h7vgHbb4L3sFLGkVeCEnth7tjg,22253
|
|
21
|
+
itkdb_gtk/uploadTest.py,sha256=xqlWvQRWiFuuUPJSvOycqn1OUYwWg_VMMMNgTDM6H_U,13120
|
|
22
|
+
itkdb_gtk-0.0.16.dev0.dist-info/METADATA,sha256=sbEASDVsH8ewZWzr62rcYLJKPg8bW_9HwtbORTufosk,3080
|
|
23
|
+
itkdb_gtk-0.0.16.dev0.dist-info/WHEEL,sha256=oiQVh_5PnQM0E3gPdiz09WCNmwiHDMaGer_elqB3coM,92
|
|
24
|
+
itkdb_gtk-0.0.16.dev0.dist-info/entry_points.txt,sha256=O8Epj2DiRBR3c0BFMbNVJPzRwYtFNEHNp9IQjGUjEKc,331
|
|
25
|
+
itkdb_gtk-0.0.16.dev0.dist-info/top_level.txt,sha256=KVRrH4OS8ovzNR9bvADE0ABn5bNpSk987tuH0jCfkbU,10
|
|
26
|
+
itkdb_gtk-0.0.16.dev0.dist-info/RECORD,,
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
[gui_scripts]
|
|
2
2
|
getShipments = itkdb_gtk:getShipments
|
|
3
3
|
glueWeight = itkdb_gtk:glueWeight
|
|
4
|
-
|
|
4
|
+
groundVITests = itkdb_gtk:groundVITests
|
|
5
5
|
itkdb_dashBoard = itkdb_gtk:dash_board
|
|
6
6
|
sendShipments = itkdb_gtk:sendShipments
|
|
7
|
+
uploadIVfiles = itkdb_gtk:uploadIVfiles
|
|
7
8
|
uploadMultipleTests = itkdb_gtk:uploadMultipleTests
|
|
8
9
|
uploadTest = itkdb_gtk:uploadTest
|
itkdb_gtk/checkComponent.py
DELETED
|
@@ -1,151 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env python3
|
|
2
|
-
"""Check children of DB component."""
|
|
3
|
-
|
|
4
|
-
try:
|
|
5
|
-
import readAVSdata
|
|
6
|
-
import ITkDBlogin
|
|
7
|
-
import ITkDButils
|
|
8
|
-
|
|
9
|
-
from dbGtkUtils import replace_in_container, DictDialog, ask_for_confirmation
|
|
10
|
-
|
|
11
|
-
except ModuleNotFoundError:
|
|
12
|
-
from itkdb_gtk import readAVSdata, ITkDBlogin, ITkDButils
|
|
13
|
-
from itkdb_gtk.dbGtkUtils import replace_in_container, DictDialog, ask_for_confirmation
|
|
14
|
-
|
|
15
|
-
import json
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
def ascii_complain(main_msg, secondary_msg=None):
|
|
19
|
-
"""Prints an error message
|
|
20
|
-
|
|
21
|
-
Args:
|
|
22
|
-
-----
|
|
23
|
-
main (): Main message
|
|
24
|
-
secondary (): Seconday message
|
|
25
|
-
"""
|
|
26
|
-
print("**Error\n{}".format(main_msg))
|
|
27
|
-
if secondary_msg:
|
|
28
|
-
msg = secondary_msg.replace("\n", "\n\t")
|
|
29
|
-
print("\t{}".format(msg))
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
def find_petal(session, SN, silent=False):
|
|
33
|
-
"""Finds petal with given SN."""
|
|
34
|
-
try:
|
|
35
|
-
petal_core = ITkDButils.get_DB_component(session, SN)
|
|
36
|
-
|
|
37
|
-
except Exception as E:
|
|
38
|
-
if not silent:
|
|
39
|
-
ascii_complain("Could not find Petal Core in DB", str(E))
|
|
40
|
-
|
|
41
|
-
petal_core = None
|
|
42
|
-
return
|
|
43
|
-
|
|
44
|
-
try:
|
|
45
|
-
if petal_core["type"]["code"] != "CORE_AVS":
|
|
46
|
-
ascii_complain("Wrong component type", "This is not an AVS petal core")
|
|
47
|
-
|
|
48
|
-
# print(json.dumps(petal_core, indent=3))
|
|
49
|
-
|
|
50
|
-
except KeyError:
|
|
51
|
-
# Petal is not there
|
|
52
|
-
petal_core = None
|
|
53
|
-
|
|
54
|
-
return petal_core
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
def get_type(child):
|
|
58
|
-
"""Return object type
|
|
59
|
-
|
|
60
|
-
Args:
|
|
61
|
-
-----
|
|
62
|
-
child (): object
|
|
63
|
-
|
|
64
|
-
Returns
|
|
65
|
-
-------
|
|
66
|
-
str: object type
|
|
67
|
-
|
|
68
|
-
"""
|
|
69
|
-
if child["type"] is not None:
|
|
70
|
-
ctype = child["type"]["code"]
|
|
71
|
-
else:
|
|
72
|
-
ctype = child["componentType"]["code"]
|
|
73
|
-
|
|
74
|
-
return ctype
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
def main():
|
|
78
|
-
"""Main entry point."""
|
|
79
|
-
# ITk_PB authentication
|
|
80
|
-
dlg = ITkDBlogin.ITkDBlogin()
|
|
81
|
-
session = dlg.get_client()
|
|
82
|
-
|
|
83
|
-
final_stage = {
|
|
84
|
-
"BT_PETAL_FRONT": "COMPLETED",
|
|
85
|
-
"BT_PETAL_BACK": "COMPLETED",
|
|
86
|
-
"COOLING_LOOP_PETAL": "CLINCORE",
|
|
87
|
-
"THERMALFOAMSET_PETAL": "IN_CORE"
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
# find all cores
|
|
91
|
-
# Now all the objects
|
|
92
|
-
payload = {
|
|
93
|
-
"componentType": ["BT"],
|
|
94
|
-
"componentType": ["CORE_PETAL"],
|
|
95
|
-
"type": ["CORE_AVS"],
|
|
96
|
-
}
|
|
97
|
-
core_list = session.get("listComponents", json=payload)
|
|
98
|
-
|
|
99
|
-
for obj in core_list:
|
|
100
|
-
SN = obj["serialNumber"]
|
|
101
|
-
id = obj['alternativeIdentifier']
|
|
102
|
-
if "PPB" not in id:
|
|
103
|
-
continue
|
|
104
|
-
|
|
105
|
-
core = find_petal(session, SN)
|
|
106
|
-
if core is None:
|
|
107
|
-
print("SN: not a petal core.")
|
|
108
|
-
continue
|
|
109
|
-
|
|
110
|
-
location = core["currentLocation"]['code']
|
|
111
|
-
stage = core["currentStage"]['code']
|
|
112
|
-
if stage != "AT_QC_SITE":
|
|
113
|
-
rc = ITkDButils.set_object_stage(session, SN, "AT_QC_SITE")
|
|
114
|
-
if rc is not None:
|
|
115
|
-
print("problems setting stage")
|
|
116
|
-
|
|
117
|
-
if "children" not in core:
|
|
118
|
-
ascii_complain("{}[{}]".format(SN, id), "Not assembled")
|
|
119
|
-
continue
|
|
120
|
-
|
|
121
|
-
print("Petal {} [{}] - {}. {}".format(SN, id, stage, location))
|
|
122
|
-
clist = []
|
|
123
|
-
for child in core["children"]:
|
|
124
|
-
cstage = "Missing"
|
|
125
|
-
if child["component"] is None:
|
|
126
|
-
ctype = get_type(child)
|
|
127
|
-
clist.append((ctype, cstage, None, None))
|
|
128
|
-
|
|
129
|
-
else:
|
|
130
|
-
SN = child["component"]["serialNumber"]
|
|
131
|
-
ctype = get_type(child)
|
|
132
|
-
cobj = ITkDButils.get_DB_component(session, SN)
|
|
133
|
-
cstage = cobj["currentStage"]['code']
|
|
134
|
-
if cstage != final_stage[ctype]:
|
|
135
|
-
rc = ITkDButils.set_object_stage(session, SN, final_stage[ctype])
|
|
136
|
-
if rc is not None:
|
|
137
|
-
cstage = final_stage[ctype]
|
|
138
|
-
|
|
139
|
-
clocation = cobj["currentLocation"]['code']
|
|
140
|
-
clist.append((ctype, cstage, SN, clocation))
|
|
141
|
-
|
|
142
|
-
for item in clist:
|
|
143
|
-
print("\t{} [{}] - {} at {}".format(item[2], item[0], item[1], item[3]))
|
|
144
|
-
|
|
145
|
-
print()
|
|
146
|
-
|
|
147
|
-
dlg.die()
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
if __name__ == "__main__":
|
|
151
|
-
main()
|
itkdb_gtk/checkJSon.py
DELETED
|
@@ -1,56 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env python3
|
|
2
|
-
"""Check tha a given JSon is valid."""
|
|
3
|
-
from pathlib import Path
|
|
4
|
-
import json
|
|
5
|
-
|
|
6
|
-
try:
|
|
7
|
-
import ITkDBlogin
|
|
8
|
-
import ITkDButils
|
|
9
|
-
except ModuleNotFoundError:
|
|
10
|
-
from itkdb_gtk import ITkDBlogin, ITkDButils
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
def checkJSOn(session, ifile):
|
|
14
|
-
"""Check teh validity of a JSon test file
|
|
15
|
-
|
|
16
|
-
Args:
|
|
17
|
-
fname (): File or data.
|
|
18
|
-
"""
|
|
19
|
-
fnam = Path(ifile).expanduser().resolve()
|
|
20
|
-
with open(fnam, 'r') as fin:
|
|
21
|
-
user_file = json.load(fin)
|
|
22
|
-
|
|
23
|
-
test_type = user_file["testType"]
|
|
24
|
-
component = ITkDButils.get_DB_component(session, user_file["component"])
|
|
25
|
-
|
|
26
|
-
skeleton = ITkDButils.get_test_skeleton(session,
|
|
27
|
-
component["componentType"]["code"],
|
|
28
|
-
test_type)
|
|
29
|
-
|
|
30
|
-
for key in skeleton.keys():
|
|
31
|
-
if key in ["comments", "defects"]:
|
|
32
|
-
continue
|
|
33
|
-
|
|
34
|
-
if key not in user_file:
|
|
35
|
-
print("Missing key {}".format(key))
|
|
36
|
-
if key == "institution":
|
|
37
|
-
sites = session.get("listInstitutions", json={})
|
|
38
|
-
print(sites)
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
if __name__ == "__main__":
|
|
42
|
-
import sys
|
|
43
|
-
dlg = ITkDBlogin.ITkDBlogin()
|
|
44
|
-
client = dlg.get_client()
|
|
45
|
-
if client is None:
|
|
46
|
-
print("Could not connect to DB with provided credentials.")
|
|
47
|
-
dlg.die()
|
|
48
|
-
sys.exit()
|
|
49
|
-
|
|
50
|
-
try:
|
|
51
|
-
checkJSOn(client, sys.argv[1])
|
|
52
|
-
|
|
53
|
-
except Exception as ex:
|
|
54
|
-
print(ex)
|
|
55
|
-
|
|
56
|
-
dlg.die()
|
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
itkdb_gtk/GlueWeight.py,sha256=1Ssu6m_KL1PAHHI76yn9bnqSLSqxbc--S-DtV2V1L4g,12294
|
|
2
|
-
itkdb_gtk/ITkDB.desktop,sha256=v_K4mHsDxb912J1XGo6mOlbW2TkHvYNGrKmiOnsBQqM,172
|
|
3
|
-
itkdb_gtk/ITkDB.svg,sha256=Rb1DyhhGj504-h3vi-H6BF_Gm-OUciIXWOmzZbjGns4,23991
|
|
4
|
-
itkdb_gtk/ITkDBlogin.py,sha256=NgDoBoo8Le3Gfoo-w1casKs0mCD4fibZ7NG3esEBiQM,9902
|
|
5
|
-
itkdb_gtk/ITkDButils.py,sha256=7FPUiUhunWUprpHhrD1uD2zAAD15ZYJhH_Tu-jNw30U,14850
|
|
6
|
-
itkdb_gtk/ShowAttachments.py,sha256=yHa3W1_KtDEGBEcLjGsCONKDP0ntDJNggi3T1bc48Yg,4693
|
|
7
|
-
itkdb_gtk/ShowComments.py,sha256=Poyx3bljWEMwhB2FDvBVMSRPcqv9aowlDtbbcs8JgYw,2989
|
|
8
|
-
itkdb_gtk/ShowDefects.py,sha256=hnXZKfGshoTBJindbjrNgO6kKpVXwKO8Cu6Txn4cCXE,3329
|
|
9
|
-
itkdb_gtk/__init__.py,sha256=Z1pERIIm95T9Df-IoSBMMHSrBvN--sZzVtIxOUIjBbM,686
|
|
10
|
-
itkdb_gtk/checkComponent.py,sha256=bB6xvCDoLWXUT9eFDoI6tg_yQbKnzxtYRCYOA5IgSyM,3979
|
|
11
|
-
itkdb_gtk/checkJSon.py,sha256=AqPy7Pq5kgZgnHMPa0fgM39RERHuI4uIlZ8qNRUaoFc,1432
|
|
12
|
-
itkdb_gtk/dashBoard.py,sha256=PrF8F-7wiCVU-fquKcCqaTi4MX5g7-tHm__yo-oauNk,4412
|
|
13
|
-
itkdb_gtk/dbGtkUtils.py,sha256=_93BlN5iy0YJG47FqeGXJQsQHN8DgvkJDVMoh_4cE_4,20713
|
|
14
|
-
itkdb_gtk/getShipments.py,sha256=6xNTFAQ1Xon8M20U5BSRJkRc4P7vfNuG4liktoMTaa0,18718
|
|
15
|
-
itkdb_gtk/gndVITests.py,sha256=nvTqj35hxypYWDF4sllwxgkQ9QEqqfqKBtxkjf4CMPA,8046
|
|
16
|
-
itkdb_gtk/readAVSdata.py,sha256=VCoCece2tuhbd7yfaCCTXuRbGEFUUV2gCcJozQYhPRE,19379
|
|
17
|
-
itkdb_gtk/readGoogleSheet.py,sha256=cQ_pVsS_nwUh0bnXl7AP4in9kQ3Q-p8BIvXvvrTRInc,2679
|
|
18
|
-
itkdb_gtk/sendShipments.py,sha256=yaKQ30fMG7bt3Zk7Rkgmla04nqfboA8zg3a-rleG9-g,13133
|
|
19
|
-
itkdb_gtk/uploadMultipleTests.py,sha256=anbn9_2AGmgfcNZozIowEvpBG---K36Kihx_M2j4J50,19892
|
|
20
|
-
itkdb_gtk/uploadPetalInformation.py,sha256=zXcZEvDj9jzOUSUzzvyLoHvQURSCQ01C5gidHZb4ZP0,22252
|
|
21
|
-
itkdb_gtk/uploadTest.py,sha256=O6PynyN8jNIo7YCB-TKpN8qfh7pcqE6lPA06CAMFtvY,12154
|
|
22
|
-
itkdb_gtk-0.0.12.dist-info/METADATA,sha256=svtSC25f0fif_Lfql9gHsTJg5w2DaO_gKOi9Q05SZZs,2824
|
|
23
|
-
itkdb_gtk-0.0.12.dist-info/WHEEL,sha256=pkctZYzUS4AYVn6dJ-7367OJZivF2e8RA9b_ZBjif18,92
|
|
24
|
-
itkdb_gtk-0.0.12.dist-info/entry_points.txt,sha256=BKe3-TsAnWjLgCJE8c_knkWcWHMFxyKCxheoPbkEtuk,289
|
|
25
|
-
itkdb_gtk-0.0.12.dist-info/top_level.txt,sha256=KVRrH4OS8ovzNR9bvADE0ABn5bNpSk987tuH0jCfkbU,10
|
|
26
|
-
itkdb_gtk-0.0.12.dist-info/RECORD,,
|
|
File without changes
|