eva-shell 0.2.37__tar.gz → 0.2.39__tar.gz

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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: eva-shell
3
- Version: 0.2.37
3
+ Version: 0.2.39
4
4
  Summary: EVA ICS v4 shell
5
5
  Home-page: https://github.com/eva-ics/eva4
6
6
  Author: Bohemia Automation / Altertech
@@ -1,3 +1,3 @@
1
- __version__ = '0.2.37'
1
+ __version__ = '0.2.39'
2
2
 
3
3
  DEFAULT_REPOSITORY_URL = 'https://pub.bma.ai/eva4'
@@ -12,7 +12,7 @@ neotermcolor.readline_always_safe = True
12
12
 
13
13
  from .sharedobj import common, current_command
14
14
  from .tools import print_tb, err, is_local_shell
15
- from .compl import ComplOID, ComplSvc, ComplNode, ComplDeployFile, ComplDobj
15
+ from .compl import ComplOID, ComplSvc, ComplNode, ComplDeployFile, ComplAnyFile, ComplDobj
16
16
  from .compl import ComplOIDtp, ComplSvcRpcMethod, ComplSvcRpcParams, ComplEdit
17
17
  from .client import call_rpc, DEFAULT_DB_SERVICE, DEFAULT_REPL_SERVICE
18
18
  from .client import DEFAULT_ACL_SERVICE, DEFAULT_AUTH_SERVICE
@@ -523,6 +523,12 @@ def append_svc_cli(root_sp):
523
523
  'purge', help='purge service (destroy and delete all service data)')
524
524
  p.add_argument('i', metavar='SVC').completer = ComplSvc()
525
525
 
526
+ p = sp.add_parser('flash', help='flash the service binary')
527
+ p.add_argument('i', metavar='SVC').completer = ComplSvc()
528
+ p.add_argument(
529
+ 'file', metavar='FILE',
530
+ help='service file to reflash with').completer = ComplAnyFile()
531
+
526
532
 
527
533
  def append_acl_cli(root_sp):
528
534
  ap = root_sp.add_parser('acl', help='ACL commands')
@@ -764,6 +770,9 @@ def append_item_cli(root_sp):
764
770
  p.add_argument('i', metavar='MASK').completer = ComplOID('state')
765
771
  p.add_argument('-y', '--full', action='store_true')
766
772
 
773
+ p = sp.add_parser('stream-info', help='item stream info')
774
+ p.add_argument('i', metavar='MASK').completer = ComplOID('state')
775
+
767
776
  p = sp.add_parser('history', help='item state history')
768
777
  p.add_argument('i', metavar='OID').completer = ComplOID('state')
769
778
  p.add_argument('-a',
@@ -820,6 +829,12 @@ def append_item_cli(root_sp):
820
829
 
821
830
  p = sp.add_parser('create', help='create an item')
822
831
  p.add_argument('i', metavar='OID').completer = ComplOID()
832
+ p.add_argument(
833
+ '-p',
834
+ '--python',
835
+ help=
836
+ 'For Python lmacro: assign eva.controller.py as action svc and edit code after creation',
837
+ action='store_true')
823
838
 
824
839
  p = sp.add_parser('destroy', help='destroy item(s)')
825
840
  p.add_argument('i', metavar='MASK').completer = ComplOID()
@@ -832,6 +847,10 @@ def append_item_cli(root_sp):
832
847
 
833
848
  p = sp.add_parser('edit', help='edit item config')
834
849
  p.add_argument('i', metavar='OID').completer = ComplOID()
850
+ p.add_argument('-p',
851
+ '--python',
852
+ help='For Python lmacro: edit code',
853
+ action='store_true')
835
854
 
836
855
  p = sp.add_parser('set', help='set item state')
837
856
  p.add_argument('i', metavar='OID').completer = ComplOID()
@@ -1183,6 +1202,7 @@ def append_cloud_cli(root_sp):
1183
1202
  help='update without any confirmations',
1184
1203
  action='store_true')
1185
1204
 
1205
+
1186
1206
  def append_video_cli(root_sp):
1187
1207
  ap_generator = root_sp.add_parser('video', help='video commands')
1188
1208
  sp_generator = ap_generator.add_subparsers(dest='_subc', help='sub command')
@@ -1192,12 +1212,8 @@ def append_video_cli(root_sp):
1192
1212
 
1193
1213
  p = sp.add_parser('create', help='create a video recording')
1194
1214
  p.add_argument('i', metavar='source')
1195
- p.add_argument('--keep',
1196
- type=float,
1197
- help='Keep (seconds)')
1198
- p.add_argument('--enabled',
1199
- help='Enable recording',
1200
- action='store_true')
1215
+ p.add_argument('--keep', type=float, help='Keep (seconds)')
1216
+ p.add_argument('--enabled', help='Enable recording', action='store_true')
1201
1217
  p.add_argument(
1202
1218
  '-a',
1203
1219
  '--video-svc',
@@ -1243,7 +1259,8 @@ def append_video_cli(root_sp):
1243
1259
  help=f'video service (default: {DEFAULT_VIDEO_SERVICE})',
1244
1260
  default=DEFAULT_VIDEO_SERVICE).completer = ComplSvc('videosrv')
1245
1261
 
1246
- p = sp.add_parser('export', help='export video recording config(s) to a deployment file')
1262
+ p = sp.add_parser(
1263
+ 'export', help='export video recording config(s) to a deployment file')
1247
1264
  p.add_argument('i', metavar='MASK')
1248
1265
  p.add_argument(
1249
1266
  '-a',
@@ -1253,7 +1270,8 @@ def append_video_cli(root_sp):
1253
1270
  p.add_argument('-o', '--output', metavar='FILE',
1254
1271
  help='output file').completer = ComplDeployFile()
1255
1272
 
1256
- p = sp.add_parser('deploy', help='deploy video recording(s) from a deployment file')
1273
+ p = sp.add_parser('deploy',
1274
+ help='deploy video recording(s) from a deployment file')
1257
1275
  p.add_argument(
1258
1276
  '-a',
1259
1277
  '--video-svc',
@@ -1262,8 +1280,8 @@ def append_video_cli(root_sp):
1262
1280
  p.add_argument('-f', '--file', metavar='FILE',
1263
1281
  help='deployment file').completer = ComplDeployFile()
1264
1282
 
1265
- p = sp.add_parser('undeploy',
1266
- help='undeploy video recordings(s) using a deployment file')
1283
+ p = sp.add_parser(
1284
+ 'undeploy', help='undeploy video recordings(s) using a deployment file')
1267
1285
  p.add_argument(
1268
1286
  '-a',
1269
1287
  '--video-svc',
@@ -1272,6 +1290,7 @@ def append_video_cli(root_sp):
1272
1290
  p.add_argument('-f', '--file', metavar='FILE',
1273
1291
  help='deployment file').completer = ComplDeployFile()
1274
1292
 
1293
+
1275
1294
  def append_generator_cli(root_sp):
1276
1295
  source_types = [
1277
1296
  'random', 'random_float', 'counter', 'time', 'wave', 'udp_float'
@@ -6,20 +6,18 @@ from functools import partial
6
6
  from collections import OrderedDict
7
7
 
8
8
  import busrt
9
- from evaics.sdk import pack
9
+ from evaics.sdk import pack, VideoFrame
10
10
  from neotermcolor import colored
11
11
  from rapidtables import format_table, FORMAT_GENERATOR, FORMAT_GENERATOR_COLS
12
12
 
13
13
  from .tools import print_result, ok
14
14
  from .tools import edit_config, edit_remote_file, read_file, write_file
15
15
  from .tools import print_action_result, format_value, prepare_time, err, warn
16
- from .tools import get_node_svc_info, edit_file, get_term_size, exec_cmd, xc
16
+ from .tools import get_node_svc_info, get_term_size, exec_cmd, xc
17
17
  from .tools import get_my_ip, check_local_shell
18
18
  from .client import call_rpc, DEFAULT_REPL_SERVICE, connect
19
19
  from .sharedobj import common, current_command
20
20
 
21
- from . import DEFAULT_REPOSITORY_URL
22
-
23
21
 
24
22
  def eva_control_c(c, pfx=''):
25
23
  check_local_shell()
@@ -27,6 +25,12 @@ def eva_control_c(c, pfx=''):
27
25
  os.system(cmd)
28
26
 
29
27
 
28
+ def format_python_fname(i):
29
+ short_id = i.rsplit('/', 1)[-1].rsplit(':', 1)[-1]
30
+ fname = f'xc/py/{short_id}.py'
31
+ return fname
32
+
33
+
30
34
  class CLI:
31
35
 
32
36
  def __init__(self, *args, **kwargs):
@@ -661,6 +665,11 @@ class CLI:
661
665
  call_rpc('svc.restart', dict(i=i))
662
666
  ok()
663
667
 
668
+ def svc_flash(self, i, file):
669
+ binary = open(file, 'rb').read()
670
+ call_rpc('svc.flash', dict(i=i, binary=binary))
671
+ ok()
672
+
664
673
  def svc_destroy(self, i):
665
674
  call_rpc('svc.undeploy', dict(svcs=[i]))
666
675
  ok()
@@ -1134,8 +1143,13 @@ class CLI:
1134
1143
  print(f'{len(items)} item(s) undeployed')
1135
1144
  print()
1136
1145
 
1137
- def item_create(self, i):
1138
- call_rpc('item.create', dict(i=i))
1146
+ def item_create(self, i, python=False):
1147
+ if python:
1148
+ cfg = {'oid': i, 'action': {'svc': 'eva.controller.py'}}
1149
+ call_rpc('item.deploy', dict(items=[cfg]))
1150
+ return self.edit(format_python_fname(i), 'eva.filemgr.main')
1151
+ else:
1152
+ call_rpc('item.create', dict(i=i))
1139
1153
  ok()
1140
1154
 
1141
1155
  def item_destroy(self, i):
@@ -1146,7 +1160,10 @@ class CLI:
1146
1160
  call_rpc('item.enable', dict(i=i))
1147
1161
  ok()
1148
1162
 
1149
- def item_edit(self, i):
1163
+ def item_edit(self, i, python=False):
1164
+
1165
+ if python:
1166
+ return self.edit(format_python_fname(i), 'eva.filemgr.main')
1150
1167
 
1151
1168
  def deploy_edited_item(cfg, i):
1152
1169
  call_rpc('item.deploy', dict(items=[cfg]))
@@ -1173,6 +1190,33 @@ class CLI:
1173
1190
  't|n=set time|f=time', 'node', 'connected', 'act'
1174
1191
  ])
1175
1192
 
1193
+ def item_stream_info(self, i):
1194
+ data = call_rpc(
1195
+ 'item.state',
1196
+ dict(i=i, include_binary_values=True),
1197
+ )
1198
+ for d in data:
1199
+ value = d['value']
1200
+ del d['value']
1201
+ if value is None:
1202
+ d['format'] = 'nodata'
1203
+ else:
1204
+ try:
1205
+ frame = VideoFrame(value)
1206
+ d['format'] = frame.format_name()
1207
+ d['dims'] = [frame.width, frame.height]
1208
+ except:
1209
+ d['format'] = 'not-a-stream'
1210
+
1211
+ print_result(data,
1212
+ cols=[
1213
+ 'oid',
1214
+ 'status',
1215
+ 'format',
1216
+ 'dims',
1217
+ 't|n=set time|f=time',
1218
+ ])
1219
+
1176
1220
  def item_slog(self, i, db_svc, time_start, time_end, time_zone, limit):
1177
1221
  time_start = prepare_time(time_start)
1178
1222
  time_end = prepare_time(time_end)
@@ -96,6 +96,38 @@ class ComplSvcRpcParams:
96
96
  if p.startswith(prefix) and not p in pp:
97
97
  yield f'{p}='
98
98
 
99
+ class ComplAnyFile:
100
+
101
+ def __call__(self, prefix, **kwargs):
102
+ import glob
103
+ expanded = None
104
+
105
+ def expand_user(pfx):
106
+ nonlocal expanded
107
+ if pfx.startswith('~'):
108
+ expanded = os.path.expanduser('~')
109
+ return expanded + pfx[1:]
110
+ else:
111
+ return pfx
112
+
113
+ def contract_user(pfx):
114
+ nonlocal expanded
115
+ if expanded is None:
116
+ return pfx
117
+ else:
118
+ return '~' + pfx[len(expanded):]
119
+
120
+ if not prefix:
121
+ masks = ['*']
122
+ else:
123
+ prefix = expand_user(prefix)
124
+ masks = [f'{prefix}*']
125
+ for mask in masks:
126
+ for f in glob.glob(mask):
127
+ yield contract_user(f)
128
+ for f in glob.glob(f'{prefix}*'):
129
+ if os.path.isdir(f):
130
+ yield contract_user(f'{f}/')
99
131
 
100
132
  class ComplDeployFile:
101
133
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: eva-shell
3
- Version: 0.2.37
3
+ Version: 0.2.39
4
4
  Summary: EVA ICS v4 shell
5
5
  Home-page: https://github.com/eva-ics/eva4
6
6
  Author: Bohemia Automation / Altertech
@@ -1,4 +1,4 @@
1
- __version__ = '0.2.37'
1
+ __version__ = '0.2.39'
2
2
 
3
3
  import setuptools
4
4
 
File without changes
File without changes
File without changes
File without changes