naeural-client 2.6.37__py3-none-any.whl → 2.6.39__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.
naeural_client/_ver.py CHANGED
@@ -1,4 +1,4 @@
1
- __VER__ = "2.6.37"
1
+ __VER__ = "2.6.39"
2
2
 
3
3
  if __name__ == "__main__":
4
4
  with open("pyproject.toml", "rt") as fd:
@@ -95,26 +95,10 @@ TODO: (future)
95
95
  - check ETH signature of the oracle data
96
96
 
97
97
  """
98
- import requests
99
98
 
100
99
  from naeural_client.utils.config import log_with_color
101
- from naeural_client import Logger
102
- from naeural_client.bc import DefaultBlockEngine
103
- from naeural_client.utils.oracle_sync.multiple_requests import oracle_tester_init, handle_command_results
100
+ from naeural_client.utils.oracle_sync.oracle_tester import oracle_tester_init, handle_command_results
104
101
 
105
- """
106
- TODOs:
107
- - test NEPCTL command in CLI too
108
- - check ETH signature of the oracle data
109
- """
110
-
111
-
112
- def _check_response(data):
113
- res = True
114
- log = Logger("NEPCTL", base_folder=".", app_folder="_local_cache", silent=True)
115
- bc = DefaultBlockEngine(name='test', log=log)
116
- print(bc.address)
117
- return res
118
102
 
119
103
  def get_availability(args):
120
104
  """
@@ -460,20 +460,37 @@ class BaseLogger(object):
460
460
  import platform
461
461
  import subprocess
462
462
  import re
463
+ import multiprocessing
463
464
  str_system = platform.system()
464
465
  if str_system == "Windows":
465
466
  self.processor_platform = platform.processor()
467
+
466
468
  elif str_system == "Darwin":
467
469
  os.environ['PATH'] = os.environ['PATH'] + os.pathsep + '/usr/sbin'
468
470
  command ="sysctl -n machdep.cpu.brand_string"
469
471
  self.processor_platform = subprocess.check_output(command, shell=True).strip().decode('utf-8')
472
+
470
473
  elif str_system == "Linux":
471
474
  command = "cat /proc/cpuinfo"
472
475
  all_info = subprocess.check_output(command, shell=True).decode().strip()
476
+ proc_platform = None
473
477
  for line in all_info.split("\n"):
474
478
  if "model name" in line:
475
- self.processor_platform = re.sub( ".*model name.*:", "", line,1)
479
+ proc_platform = re.sub( ".*model name.*:", "", line,1)
476
480
  break
481
+ if proc_platform is None:
482
+ cores = multiprocessing.cpu_count()
483
+ proc_platform = "Unknown"
484
+ try:
485
+ lscpu_out = subprocess.check_output("lscpu", shell=True).decode().strip()
486
+ match_vendor = re.search(r"Vendor ID:\s+(.*)", lscpu_out)
487
+ if match_vendor:
488
+ proc_platform = match_vendor.group(1)
489
+ except:
490
+ pass
491
+ proc_platform = f"{proc_platform} {cores} cores"
492
+ #endif no model name
493
+ self.processor_platform = proc_platform
477
494
  return
478
495
 
479
496
  def get_processor_platform(self):
@@ -10,7 +10,8 @@ from collections import defaultdict
10
10
 
11
11
  from naeural_client import Logger
12
12
  from naeural_client.bc import DefaultBlockEngine
13
- from naeural_client.utils.config import log_with_color
13
+ from naeural_client.utils.config import log_with_color, get_user_folder
14
+
14
15
 
15
16
 
16
17
  class OracleTesterConstants:
@@ -23,6 +24,7 @@ class OracleTesterConstants:
23
24
  MAX_REQUEST_ROUNDS = 10
24
25
  FREQUENCY = "frequency"
25
26
  ORACLE_DATA = "oracle_data"
27
+ DEFAULT_MIN_CERTAINTY_PRC = 0.98
26
28
 
27
29
 
28
30
  ct = OracleTesterConstants
@@ -115,8 +117,10 @@ class OracleTester:
115
117
  """
116
118
  epoch_ids = result.get("epochs")
117
119
  epoch_vals = result.get("epochs_vals")
118
- dict_certainty = result.get("oracle", {}).get("manager", {}).get("certainty", {})
119
- is_valid = result.get("oracle", {}).get("manager", {}).get("valid", False)
120
+ manager_data = result.get("oracle", {}).get("manager", {})
121
+ dict_certainty = manager_data.get("certainty", {})
122
+ is_valid = manager_data.get("valid", False)
123
+ min_certainty_prc = manager_data.get("supervisor_min_avail_prc", ct.DEFAULT_MIN_CERTAINTY_PRC)
120
124
 
121
125
  current_epochs, current_avails, current_cert = [], [], []
122
126
  for epoch_id, epoch_val in zip(epoch_ids, epoch_vals):
@@ -124,7 +128,7 @@ class OracleTester:
124
128
  current_avails.append(epoch_val)
125
129
  current_cert.append(dict_certainty.get(str(epoch_id), 0))
126
130
  # endfor epochs
127
- return current_epochs, current_avails, current_cert, is_valid
131
+ return current_epochs, current_avails, current_cert, is_valid, min_certainty_prc
128
132
 
129
133
  def handle_server_data(
130
134
  self, oracle_stats_dict: dict,
@@ -156,11 +160,13 @@ class OracleTester:
156
160
  }
157
161
  # endif first time for this sender
158
162
  current_stats = oracle_stats_dict[sender]
159
- current_epochs, current_avails, current_certs, is_valid = self.compute_epochs_availability_and_certainty(result)
163
+ # TODO: maybe automate this (have only the list of keys to go through).
164
+ current_epochs, current_avails, current_certs, is_valid, min_certainty_prc = self.compute_epochs_availability_and_certainty(result)
160
165
  stats_epochs = current_stats.get("epochs", None)
161
166
  stats_avails = current_stats.get("avails", None)
162
167
  stats_certs = current_stats.get("certs", None)
163
168
  stats_is_valid = current_stats.get("is_valid", None)
169
+ stats_min_certainty_prc = current_stats.get("min_certainty_prc", None)
164
170
  mismatches = []
165
171
  if stats_epochs is not None and current_epochs != stats_epochs:
166
172
  mismatches.append(f"epochs: {current_epochs} != {stats_epochs}")
@@ -174,6 +180,9 @@ class OracleTester:
174
180
  if stats_is_valid is not None and is_valid != stats_is_valid:
175
181
  mismatches.append(f"validity: {is_valid} != {stats_is_valid}")
176
182
  # endif check for mismatch
183
+ if stats_min_certainty_prc is not None and min_certainty_prc != stats_min_certainty_prc:
184
+ mismatches.append(f"min_certainty_prc: {min_certainty_prc} != {stats_min_certainty_prc}")
185
+ # endif check for mismatch
177
186
 
178
187
  if len(mismatches) > 0:
179
188
  current_stats["errors"].append(f"Round {self.request_rounds}: {', '.join(mismatches)}")
@@ -187,6 +196,8 @@ class OracleTester:
187
196
  current_stats["certs"] = current_certs
188
197
  if stats_is_valid is None:
189
198
  current_stats["is_valid"] = is_valid
199
+ if stats_min_certainty_prc is None:
200
+ current_stats["min_certainty_prc"] = min_certainty_prc
190
201
  # endif valid data received
191
202
  return
192
203
 
@@ -298,6 +309,78 @@ class OracleTester:
298
309
  self.P(f'Finished gathering data for {len(nodes)} nodes and {self.max_request_rounds}.')
299
310
  return responses, stats_dict
300
311
 
312
+ def gather_and_compare(self, nodes, request_kwargs=None, debug=False, rounds=None):
313
+ """
314
+ Gather data from the oracle server for the given nodes and compare the results between oracles.
315
+
316
+ Parameters
317
+ ----------
318
+ nodes : list[dict] or list[str]
319
+ The list of nodes for which to gather data. Each node can be a dictionary containing the
320
+ address, eth_address, and alias of the node or a string containing the eth_address of the node.
321
+ Either way, the eth_address is required.
322
+ request_kwargs : dict
323
+ The request kwargs to be used for the request. Default None.
324
+ debug : bool
325
+ Whether to enable debug mode or not. If enabled the function will exit after one request round.
326
+
327
+ Returns
328
+ -------
329
+ tuple
330
+ A tuple containing the responses and the stats dictionary.
331
+ """
332
+ responses, stats_dict = self.gather(
333
+ nodes=nodes,
334
+ request_kwargs=request_kwargs,
335
+ debug=debug,
336
+ rounds=rounds
337
+ )
338
+ # Statistics for each node of each epoch
339
+ epochs_nodes_stats = {}
340
+ # Statistics for each epoch of each node
341
+ nodes_epochs_stats = {}
342
+ for node_eth_addr, node_data in stats_dict.items():
343
+ oracle_data = node_data.get(ct.ORACLE_DATA, {})
344
+ errors = oracle_data.get("errors", [])
345
+ if len(errors) > 0:
346
+ self.P(f'#######################{node_eth_addr} errors########################')
347
+ self.P(f"Errors for {node_eth_addr}:\n" + '\n'.join(errors), color='r')
348
+ self.P(f'#######################{node_eth_addr} errors########################')
349
+ # endif
350
+
351
+ if node_eth_addr not in nodes_epochs_stats:
352
+ # This check should not be necessary, but just in case
353
+ nodes_epochs_stats[node_eth_addr] = {}
354
+ # endif first time for this node
355
+
356
+ epochs_stats = nodes_epochs_stats[node_eth_addr]
357
+ epochs = oracle_data.get("epochs", []),
358
+ avails = oracle_data.get("avails", []),
359
+ certs = oracle_data.get("certs", [])
360
+ min_certainty_prc = oracle_data.get("stats_min_certainty_prc", ct.DEFAULT_MIN_CERTAINTY_PRC)
361
+ for epoch, avail, cert in zip(epochs, avails, certs):
362
+ if epoch not in epochs_nodes_stats:
363
+ epochs_nodes_stats[epoch] = {}
364
+ # endif epoch not in stats
365
+ if epoch not in epochs_stats:
366
+ epochs_stats[epoch] = {}
367
+ # endif epoch not in stats
368
+ node_stats = epochs_nodes_stats[epoch]
369
+
370
+ if cert >= min_certainty_prc:
371
+ if avail not in epochs_stats[epoch]:
372
+ epochs_stats[epoch][avail] = set()
373
+ if avail not in node_stats:
374
+ node_stats[avail] = set()
375
+ # endif first time encountering this availability
376
+ epochs_stats[epoch][avail].add(node_eth_addr)
377
+ node_stats[avail].add(node_eth_addr)
378
+ # endif valid data
379
+ # endfor each epoch
380
+
381
+
382
+ return responses, stats_dict
383
+
301
384
  def get_current_epoch(self):
302
385
  epoch_url = self.BASE_URL + self.CURRENT_EPOCH_ENDPOINT
303
386
  response = self.make_request(epoch_url)
@@ -490,8 +573,14 @@ def handle_command_results(res):
490
573
  return
491
574
 
492
575
  def oracle_tester_init(silent=True, **kwargs):
493
- log = Logger("R1CTL", base_folder=".", app_folder="_local_cache", silent=silent)
576
+ log = Logger(
577
+ "R1CTL",
578
+ base_folder=get_user_folder(),
579
+ app_folder="_local_cache",
580
+ silent=silent
581
+ )
494
582
  bc = DefaultBlockEngine(name='R1CTL', log=log)
583
+
495
584
  tester = OracleTester(
496
585
  bce=bc,
497
586
  log=log,
@@ -521,6 +610,40 @@ def test_commands():
521
610
  handle_command_results(res)
522
611
  return
523
612
 
613
+ def oracle_check(N=10):
614
+ import random
615
+ random.seed(42)
616
+
617
+ tester = oracle_tester_init(
618
+ silent=True,
619
+ interval_seconds=0.2,
620
+ )
621
+ current_epoch = tester.get_current_epoch()
622
+ if current_epoch is None:
623
+ current_epoch = 100
624
+ nodes = tester.get_active_nodes()
625
+ rounds = 5
626
+ max_epochs = 10
627
+ max_nodes = 5
628
+
629
+ nodes = nodes[:max_nodes]
630
+ for i in range(N):
631
+ start = random.randint(1, current_epoch - 1)
632
+ end = random.randint(start, current_epoch - 1)
633
+ end = min(end, start + max_epochs - 1)
634
+
635
+ tester.P(f'Test {i + 1}/{N}: Epochs {start} to {end} with {rounds} rounds:', show=True)
636
+ tester.gather_and_compare(
637
+ nodes=nodes,
638
+ request_kwargs={
639
+ "start_epoch": start,
640
+ "end_epoch": end
641
+ },
642
+ )
643
+ tester.P(f'Finished test {i + 1}/{N}', show=True)
644
+ # endfor each test
645
+ return
646
+
524
647
  def oracle_test(N=10):
525
648
  import random
526
649
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: naeural_client
3
- Version: 2.6.37
3
+ Version: 2.6.39
4
4
  Summary: `naeural_client` is the Python SDK required for client app development for the Naeural Edge Protocol Edge Protocol framework
5
5
  Project-URL: Homepage, https://github.com/NaeuralEdgeProtocol/naeural_client
6
6
  Project-URL: Bug Tracker, https://github.com/NaeuralEdgeProtocol/naeural_client/issues
@@ -1,5 +1,5 @@
1
1
  naeural_client/__init__.py,sha256=YimqgDbjLuywsf8zCWE0EaUXH4MBUrqLxt0TDV558hQ,632
2
- naeural_client/_ver.py,sha256=Kz07pCrAEvKbAHrCINS6PyoSTVp83A2pwXAu8UB_eUc,331
2
+ naeural_client/_ver.py,sha256=LKmpmF9zipVxTAWBLJnSORTzUky-UsiIPtU_RbkZbB8,331
3
3
  naeural_client/base_decentra_object.py,sha256=C4iwZTkhKNBS4VHlJs5DfElRYLo4Q9l1V1DNVSk1fyQ,4412
4
4
  naeural_client/plugins_manager_mixin.py,sha256=X1JdGLDz0gN1rPnTN_5mJXR8JmqoBFQISJXmPR9yvCo,11106
5
5
  naeural_client/base/__init__.py,sha256=hACh83_cIv7-PwYMM3bQm2IBmNqiHw-3PAfDfAEKz9A,259
@@ -23,7 +23,7 @@ naeural_client/cli/README.md,sha256=WPdI_EjzAbUW1aPyj1sSR8rLydcJKZtoiaEtklQrjHo,
23
23
  naeural_client/cli/cli.py,sha256=EC7-ehOMQJ_Dq7R9TTrajpvQWwdalAOgb1JAeBGHF50,3830
24
24
  naeural_client/cli/cli_commands.py,sha256=Gfims_TqaBi2QWM-6yxd_B_CETF8mmt7oEDPTg59lcI,2821
25
25
  naeural_client/cli/nodes.py,sha256=QXSniYy3Phr6buoVV-HUDRYuF5YQDUgf6nT6EzDyMJw,4909
26
- naeural_client/cli/oracles.py,sha256=g8h8kl3Mu6gU7JCs4a6WSDpvuVDGJgTHJbYJy7Iriw0,5210
26
+ naeural_client/cli/oracles.py,sha256=Y_PzHshfSERS_Utjjtw5d_BsQRdGr6P4L6uW8yTdA0M,4809
27
27
  naeural_client/code_cheker/__init__.py,sha256=pwkdeZGVL16ZA4Qf2mRahEhoOvKhL7FyuQbMFLr1E5M,33
28
28
  naeural_client/code_cheker/base.py,sha256=lT5DRIFO5rqzsMNCmdMRfkAeevmezozehyfgmhnKpuI,19074
29
29
  naeural_client/code_cheker/checker.py,sha256=QWupeM7ToancVIq1tRUxRNUrI8B5l5eoY0kDU4-O5aE,7365
@@ -58,7 +58,7 @@ naeural_client/io_formatter/default/a_dummy.py,sha256=qr9eUizQ-NN5jdXVzkaZKMaf9K
58
58
  naeural_client/io_formatter/default/aixp1.py,sha256=MX0TeUR4APA-qN3vUC6uzcz8Pssz5lgrQWo7td5Ri1A,3052
59
59
  naeural_client/io_formatter/default/default.py,sha256=gEy78cP2D5s0y8vQh4aHuxqz7D10gGfuiKF311QhrpE,494
60
60
  naeural_client/logging/__init__.py,sha256=b79X45VC6c37u32flKB2GAK9f-RR0ocwP0JDCy0t7QQ,33
61
- naeural_client/logging/base_logger.py,sha256=dTGQeIQADPFPlNv-3TR4uXi61y-N6_TLOfosmONuKv8,67113
61
+ naeural_client/logging/base_logger.py,sha256=sTdY0IudHyJKluKkJexyR4ZCZvO1XVKwKMjc1LeOL5E,67694
62
62
  naeural_client/logging/small_logger.py,sha256=m12hCb_H4XifJYYfgCAOUDkcXm-h4pSODnFf277OFVI,2937
63
63
  naeural_client/logging/logger_mixins/__init__.py,sha256=yQO7umlRvz63FeWpi-F9GRmC_MOHcNW6R6pwvZZBy3A,600
64
64
  naeural_client/logging/logger_mixins/class_instance_mixin.py,sha256=xUXE2VZgmrlrSrvw0f6GF1jlTnVLeVkIiG0bhlBfq3o,2741
@@ -82,9 +82,9 @@ naeural_client/utils/__init__.py,sha256=mAnke3-MeRzz3nhQvhuHqLnpaaCSmDxicd7Ck9uw
82
82
  naeural_client/utils/comm_utils.py,sha256=4cS9llRr_pK_3rNgDcRMCQwYPO0kcNU7AdWy_LtMyCY,1072
83
83
  naeural_client/utils/config.py,sha256=Ub5sw3NG6wskAF5C4s0WU0rzXHVLy70ZTRU0W8HUGTM,6403
84
84
  naeural_client/utils/dotenv.py,sha256=_AgSo35n7EnQv5yDyu7C7i0kHragLJoCGydHjvOkrYY,2008
85
- naeural_client/utils/oracle_sync/multiple_requests.py,sha256=GLzROGZ0gI4d1PVWgW_JBUYZjEL4LqZvHvwelxDiPW4,20892
86
- naeural_client-2.6.37.dist-info/METADATA,sha256=geNzXBl8TAuOA9uhBLfAd5nk_YH0aa_BWfX0hX--INs,12354
87
- naeural_client-2.6.37.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
88
- naeural_client-2.6.37.dist-info/entry_points.txt,sha256=CTua17GUrRa4aXeafezGC9TiWKGKQzwTjQmB2jyj22g,91
89
- naeural_client-2.6.37.dist-info/licenses/LICENSE,sha256=cvOsJVslde4oIaTCadabXnPqZmzcBO2f2zwXZRmJEbE,11311
90
- naeural_client-2.6.37.dist-info/RECORD,,
85
+ naeural_client/utils/oracle_sync/oracle_tester.py,sha256=wBetjbJ8Z6VjTn0y7aqxL59Z9Qy1sukJ4bGlykNf0vA,25307
86
+ naeural_client-2.6.39.dist-info/METADATA,sha256=CS5uWfA_sKzkNFWHmh4N-iv22ym-wyL5NiEZVez-6Ys,12354
87
+ naeural_client-2.6.39.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
88
+ naeural_client-2.6.39.dist-info/entry_points.txt,sha256=CTua17GUrRa4aXeafezGC9TiWKGKQzwTjQmB2jyj22g,91
89
+ naeural_client-2.6.39.dist-info/licenses/LICENSE,sha256=cvOsJVslde4oIaTCadabXnPqZmzcBO2f2zwXZRmJEbE,11311
90
+ naeural_client-2.6.39.dist-info/RECORD,,