atomicshop 2.12.15__py3-none-any.whl → 2.12.17__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 atomicshop might be problematic. Click here for more details.
- atomicshop/__init__.py +1 -1
- atomicshop/diff_check.py +95 -49
- atomicshop/monitor/change_monitor.py +77 -134
- atomicshop/monitor/checks/dns.py +100 -82
- atomicshop/monitor/checks/hash.py +39 -28
- atomicshop/monitor/checks/hash_checks/file.py +34 -35
- atomicshop/monitor/checks/hash_checks/url.py +41 -39
- atomicshop/monitor/checks/network.py +30 -28
- atomicshop/monitor/checks/process_running.py +7 -7
- atomicshop/timer.py +30 -11
- atomicshop/wrappers/loggingw/reading.py +52 -25
- {atomicshop-2.12.15.dist-info → atomicshop-2.12.17.dist-info}/METADATA +1 -1
- {atomicshop-2.12.15.dist-info → atomicshop-2.12.17.dist-info}/RECORD +16 -16
- {atomicshop-2.12.15.dist-info → atomicshop-2.12.17.dist-info}/LICENSE.txt +0 -0
- {atomicshop-2.12.15.dist-info → atomicshop-2.12.17.dist-info}/WHEEL +0 -0
- {atomicshop-2.12.15.dist-info → atomicshop-2.12.17.dist-info}/top_level.txt +0 -0
atomicshop/timer.py
CHANGED
|
@@ -7,7 +7,10 @@ class TimerError(Exception):
|
|
|
7
7
|
|
|
8
8
|
class Timer:
|
|
9
9
|
""" Custom timer class to measure elapsed time. Returns time in seconds (float) or nanoseconds with setting. """
|
|
10
|
-
def __init__(
|
|
10
|
+
def __init__(
|
|
11
|
+
self,
|
|
12
|
+
nanoseconds: bool = False
|
|
13
|
+
):
|
|
11
14
|
"""
|
|
12
15
|
Set up timer in seconds or nanoseconds
|
|
13
16
|
Seconds are returned as float, nanoseconds as int.
|
|
@@ -17,6 +20,9 @@ class Timer:
|
|
|
17
20
|
self._start_time = None
|
|
18
21
|
self._nanoseconds: bool = nanoseconds
|
|
19
22
|
|
|
23
|
+
self.running: bool = False
|
|
24
|
+
self.last_measure = None
|
|
25
|
+
|
|
20
26
|
def start(self):
|
|
21
27
|
"""Start a new timer"""
|
|
22
28
|
|
|
@@ -28,6 +34,8 @@ class Timer:
|
|
|
28
34
|
else:
|
|
29
35
|
self._start_time = time.perf_counter()
|
|
30
36
|
|
|
37
|
+
self.running = True
|
|
38
|
+
|
|
31
39
|
def restart(self):
|
|
32
40
|
"""Reset the timer"""
|
|
33
41
|
|
|
@@ -37,20 +45,31 @@ class Timer:
|
|
|
37
45
|
def measure(self):
|
|
38
46
|
"""Measure the elapsed time"""
|
|
39
47
|
|
|
40
|
-
if self._start_time is None:
|
|
41
|
-
|
|
48
|
+
# if self._start_time is None and self.last_measure is None:
|
|
49
|
+
# raise TimerError(f"Timer is not running. Use .start() to start it")
|
|
42
50
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
51
|
+
# If the timer is running, measure the elapsed time. If not, return the last measured time.
|
|
52
|
+
if self.running:
|
|
53
|
+
if self._nanoseconds:
|
|
54
|
+
self.last_measure = time.perf_counter_ns() - self._start_time
|
|
55
|
+
else:
|
|
56
|
+
self.last_measure = time.perf_counter() - self._start_time
|
|
47
57
|
|
|
48
|
-
return
|
|
58
|
+
return self.last_measure
|
|
59
|
+
|
|
60
|
+
def stop(self, measure: bool = True):
|
|
61
|
+
"""
|
|
62
|
+
Stop the timer, and report the elapsed time
|
|
63
|
+
|
|
64
|
+
:param measure: True to measure the elapsed time, False to stop the timer without measuring.
|
|
65
|
+
Measuring, means that the timer will return the elapsed time and 'self.last_measure' will be updated.
|
|
66
|
+
"""
|
|
49
67
|
|
|
50
|
-
|
|
51
|
-
|
|
68
|
+
elapsed_time = None
|
|
69
|
+
if measure:
|
|
70
|
+
elapsed_time = self.measure()
|
|
52
71
|
|
|
53
|
-
elapsed_time = self.measure()
|
|
54
72
|
self._start_time = None
|
|
73
|
+
self.running = False
|
|
55
74
|
|
|
56
75
|
return elapsed_time
|
|
@@ -7,6 +7,7 @@ from ...file_io import csvs
|
|
|
7
7
|
|
|
8
8
|
|
|
9
9
|
READING_EXISTING_LINES: list = []
|
|
10
|
+
EXISTING_LOGS_FILE_COUNT: int = 0
|
|
10
11
|
|
|
11
12
|
|
|
12
13
|
def get_logs_paths(
|
|
@@ -80,7 +81,8 @@ def get_logs_paths(
|
|
|
80
81
|
current_file_name: str = Path(single_file['file_path']).name
|
|
81
82
|
# Get the datetime object from the file name by the date pattern.
|
|
82
83
|
try:
|
|
83
|
-
datetime_object = datetimes.get_datetime_from_complex_string_by_pattern(
|
|
84
|
+
datetime_object = datetimes.get_datetime_from_complex_string_by_pattern(
|
|
85
|
+
current_file_name, date_pattern)
|
|
84
86
|
timestamp_float = datetime_object.timestamp()
|
|
85
87
|
# ValueError will be raised if the date pattern does not match the file name.
|
|
86
88
|
except ValueError:
|
|
@@ -249,6 +251,31 @@ def get_latest_lines(
|
|
|
249
251
|
time.sleep(1)
|
|
250
252
|
"""
|
|
251
253
|
|
|
254
|
+
def extract_new_lines_only(content_lines: list):
|
|
255
|
+
new_lines: list = []
|
|
256
|
+
for row in content_lines:
|
|
257
|
+
# If the row is not in the existing lines, then add it to the new lines.
|
|
258
|
+
if row not in READING_EXISTING_LINES:
|
|
259
|
+
new_lines.append(row)
|
|
260
|
+
|
|
261
|
+
if new_lines:
|
|
262
|
+
READING_EXISTING_LINES.extend(new_lines)
|
|
263
|
+
|
|
264
|
+
return new_lines
|
|
265
|
+
|
|
266
|
+
global EXISTING_LOGS_FILE_COUNT
|
|
267
|
+
|
|
268
|
+
# If the existing logs file count is 0, it means that this is the first check. We need to get the current count.
|
|
269
|
+
if EXISTING_LOGS_FILE_COUNT == 0:
|
|
270
|
+
EXISTING_LOGS_FILE_COUNT = len(get_logs_paths(
|
|
271
|
+
log_file_path=log_file_path,
|
|
272
|
+
log_type='csv'
|
|
273
|
+
))
|
|
274
|
+
|
|
275
|
+
# If the count is still 0, then there are no logs to read.
|
|
276
|
+
if EXISTING_LOGS_FILE_COUNT == 0:
|
|
277
|
+
return [], [], header
|
|
278
|
+
|
|
252
279
|
if log_type != 'csv':
|
|
253
280
|
raise ValueError('Only "csv" log type is supported.')
|
|
254
281
|
|
|
@@ -262,9 +289,6 @@ def get_latest_lines(
|
|
|
262
289
|
latest_only=True
|
|
263
290
|
)
|
|
264
291
|
|
|
265
|
-
if not latest_statistics_file_path_object:
|
|
266
|
-
return [], [], [], []
|
|
267
|
-
|
|
268
292
|
latest_statistics_file_path: str = latest_statistics_file_path_object[0]['file_path']
|
|
269
293
|
|
|
270
294
|
# Get the previous day statistics file path.
|
|
@@ -279,33 +303,36 @@ def get_latest_lines(
|
|
|
279
303
|
except KeyError:
|
|
280
304
|
pass
|
|
281
305
|
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
306
|
+
# Count all the rotated files.
|
|
307
|
+
current_log_files_count: int = len(get_logs_paths(
|
|
308
|
+
log_file_path=log_file_path,
|
|
309
|
+
log_type='csv'
|
|
310
|
+
))
|
|
311
|
+
|
|
312
|
+
# If the count of the log files is greater than the existing logs file count, it means that the rotation happened.
|
|
313
|
+
# We will read the previous day statistics file.
|
|
314
|
+
new_lines_from_previous_file: list = []
|
|
315
|
+
if current_log_files_count > EXISTING_LOGS_FILE_COUNT:
|
|
291
316
|
current_lines, header = csvs.read_csv_to_list_of_dicts_by_header(
|
|
292
317
|
previous_day_statistics_file_path, header=header, stdout=False)
|
|
293
|
-
# Handle case where source CSV is empty (rotation period)
|
|
294
|
-
READING_EXISTING_LINES.clear() # Clear existing lines to start fresh after rotation
|
|
295
318
|
|
|
296
319
|
if get_previous_file:
|
|
297
320
|
previous_file_lines = current_lines
|
|
298
321
|
|
|
299
|
-
|
|
322
|
+
EXISTING_LOGS_FILE_COUNT = current_log_files_count
|
|
300
323
|
|
|
301
|
-
|
|
302
|
-
if current_lines:
|
|
303
|
-
for row in current_lines:
|
|
304
|
-
# If the row is not in the existing lines, then add it to the new lines.
|
|
305
|
-
if row not in READING_EXISTING_LINES:
|
|
306
|
-
new_lines.append(row)
|
|
324
|
+
new_lines_from_previous_file = extract_new_lines_only(current_lines)
|
|
307
325
|
|
|
308
|
-
|
|
309
|
-
|
|
326
|
+
# empty the previous file lines, since the file is rotated.
|
|
327
|
+
READING_EXISTING_LINES.clear()
|
|
328
|
+
|
|
329
|
+
current_lines, header = csvs.read_csv_to_list_of_dicts_by_header(
|
|
330
|
+
latest_statistics_file_path, header=header, stdout=False)
|
|
331
|
+
|
|
332
|
+
new_lines = extract_new_lines_only(current_lines)
|
|
333
|
+
|
|
334
|
+
# If we have new lines from the previous file, we will add the new lines from the latest file.
|
|
335
|
+
if new_lines_from_previous_file:
|
|
336
|
+
new_lines = new_lines_from_previous_file + new_lines
|
|
310
337
|
|
|
311
|
-
return new_lines,
|
|
338
|
+
return new_lines, previous_file_lines, header
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
atomicshop/__init__.py,sha256=
|
|
1
|
+
atomicshop/__init__.py,sha256=Y0i9YbX4w6RHv1MhMq0Dp3xhWzkgeDIA2V8gJkAoNbw,124
|
|
2
2
|
atomicshop/_basics_temp.py,sha256=6cu2dd6r2dLrd1BRNcVDKTHlsHs_26Gpw8QS6v32lQ0,3699
|
|
3
3
|
atomicshop/_create_pdf_demo.py,sha256=Yi-PGZuMg0RKvQmLqVeLIZYadqEZwUm-4A9JxBl_vYA,3713
|
|
4
4
|
atomicshop/_patch_import.py,sha256=ENp55sKVJ0e6-4lBvZnpz9PQCt3Otbur7F6aXDlyje4,6334
|
|
@@ -9,7 +9,7 @@ atomicshop/config_init.py,sha256=z2RXD_mw9nQlAOpuGry1h9QT-2LhNscXgGAktN3dCVQ,249
|
|
|
9
9
|
atomicshop/console_output.py,sha256=AOSJjrRryE97PAGtgDL03IBtWSi02aNol8noDnW3k6M,4667
|
|
10
10
|
atomicshop/console_user_response.py,sha256=31HIy9QGXa7f-GVR8MzJauQ79E_ZqAeagF3Ks4GGdDU,3234
|
|
11
11
|
atomicshop/datetimes.py,sha256=olsL01S5tkXk4WPzucxujqgLOh198BLgJntDnGYukRU,15533
|
|
12
|
-
atomicshop/diff_check.py,sha256=
|
|
12
|
+
atomicshop/diff_check.py,sha256=BJIhnAgTyJ-nyw3UBKwobvF0lJuhXQ2rPu12NiYETkI,27088
|
|
13
13
|
atomicshop/dns.py,sha256=bNZOo5jVPzq7OT2qCPukXoK3zb1oOsyaelUwQEyK1SA,2500
|
|
14
14
|
atomicshop/domains.py,sha256=Rxu6JhhMqFZRcoFs69IoEd1PtYca0lMCG6F1AomP7z4,3197
|
|
15
15
|
atomicshop/emails.py,sha256=I0KyODQpIMEsNRi9YWSOL8EUPBiWyon3HRdIuSj3AEU,1410
|
|
@@ -40,7 +40,7 @@ atomicshop/sys_functions.py,sha256=MTBxRve5bh58SPvhX3gMiGqHlSBuI_rdNN1NnnBBWqI,9
|
|
|
40
40
|
atomicshop/system_resource_monitor.py,sha256=ilA3wEUJfBjQhRsHDXGH7Q05mYr5KarPjRWP8S6pCTw,13681
|
|
41
41
|
atomicshop/system_resources.py,sha256=0mhDZBEcMzToCOw5ArJhtqYjktOW6iJGdyRkJ01Cpwk,9272
|
|
42
42
|
atomicshop/tempfiles.py,sha256=uq1ve2WlWehZ3NOTXJnpBBMt6HyCdBufqedF0HyzA6k,2517
|
|
43
|
-
atomicshop/timer.py,sha256=
|
|
43
|
+
atomicshop/timer.py,sha256=7Zw1KRV0acHCRATMnanyX2MLBb63Hc-6us3rCZ9dNlY,2345
|
|
44
44
|
atomicshop/urls.py,sha256=CQl1j1kjEVDlAuYJqYD9XxPF1SUSgrmG8PjlcXNEKsQ,597
|
|
45
45
|
atomicshop/uuids.py,sha256=JSQdm3ZTJiwPQ1gYe6kU0TKS_7suwVrHc8JZDGYlydM,2214
|
|
46
46
|
atomicshop/virtualization.py,sha256=LPP4vjE0Vr10R6DA4lqhfX_WaNdDGRAZUW0Am6VeGco,494
|
|
@@ -132,15 +132,15 @@ atomicshop/mitm/engines/__reference_general/parser___reference_general.py,sha256
|
|
|
132
132
|
atomicshop/mitm/engines/__reference_general/recorder___reference_general.py,sha256=KENDVf9OwXD9gwSh4B1XxACCe7iHYjrvnW1t6F64wdE,695
|
|
133
133
|
atomicshop/mitm/engines/__reference_general/responder___reference_general.py,sha256=1AM49UaFTKA0AHw-k3SV3uH3QbG-o6ux0c-GoWkKNU0,6993
|
|
134
134
|
atomicshop/monitor/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
135
|
-
atomicshop/monitor/change_monitor.py,sha256=
|
|
135
|
+
atomicshop/monitor/change_monitor.py,sha256=ySfFCtsCFG3irV6gKr43DbbyQgmTwzG5m3FkCWDa8UI,9246
|
|
136
136
|
atomicshop/monitor/checks/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
137
|
-
atomicshop/monitor/checks/dns.py,sha256=
|
|
138
|
-
atomicshop/monitor/checks/hash.py,sha256=
|
|
139
|
-
atomicshop/monitor/checks/network.py,sha256=
|
|
140
|
-
atomicshop/monitor/checks/process_running.py,sha256=
|
|
137
|
+
atomicshop/monitor/checks/dns.py,sha256=XOMVhf2A2A8zEvQxBszL5z_DItJC0pomg_mkiMKMrug,5741
|
|
138
|
+
atomicshop/monitor/checks/hash.py,sha256=f719jU1A_rJi1ixGEHzWIZEoqpHJq4znabZnq4in9IM,2202
|
|
139
|
+
atomicshop/monitor/checks/network.py,sha256=i2jc5LRKeQJRNtOrSbkZQQCMy33No_X-SjMcXDmIh1E,3753
|
|
140
|
+
atomicshop/monitor/checks/process_running.py,sha256=pvSTa3nHDy1YH-35QkFxBUsqnCnfU5PBA_NNjp9iUNg,1889
|
|
141
141
|
atomicshop/monitor/checks/hash_checks/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
142
|
-
atomicshop/monitor/checks/hash_checks/file.py,sha256=
|
|
143
|
-
atomicshop/monitor/checks/hash_checks/url.py,sha256=
|
|
142
|
+
atomicshop/monitor/checks/hash_checks/file.py,sha256=o80UpjPNx9-AF5fYkZaP-ASHcBCE2zwGKUVRtDYKQyI,2402
|
|
143
|
+
atomicshop/monitor/checks/hash_checks/url.py,sha256=XxBNjhQZO_JlicgadqBblvt6sIRizerwM-LVCOgMCQU,3020
|
|
144
144
|
atomicshop/ssh_scripts/process_from_ipv4.py,sha256=uDBKZ2Ds20614JW1xMLr4IPB-z1LzIwy6QH5-SJ4j0s,1681
|
|
145
145
|
atomicshop/ssh_scripts/process_from_port.py,sha256=uDTkVh4zc3HOTTGv1Et3IxM3PonDJCPuFRL6rnZDQZ4,1389
|
|
146
146
|
atomicshop/wrappers/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
@@ -216,7 +216,7 @@ atomicshop/wrappers/loggingw/formatters.py,sha256=mUtcJJfmhLNrwUVYShXTmdu40dBaJu
|
|
|
216
216
|
atomicshop/wrappers/loggingw/handlers.py,sha256=qm5Fbu8eDmlstMduUe5nKUlJU5IazFkSnQizz8Qt2os,5479
|
|
217
217
|
atomicshop/wrappers/loggingw/loggers.py,sha256=DHOOTAtqkwn1xgvLHSkOiBm6yFGNuQy1kvbhG-TDog8,2374
|
|
218
218
|
atomicshop/wrappers/loggingw/loggingw.py,sha256=v9WAseZXB50LluT9rIUcRvvevg2nLVKPgz3dbGejfV0,12151
|
|
219
|
-
atomicshop/wrappers/loggingw/reading.py,sha256=
|
|
219
|
+
atomicshop/wrappers/loggingw/reading.py,sha256=CtYOwOLFHj_hqYyZx-dKUo5ZDrn3cO-f7vU4EX515xI,14980
|
|
220
220
|
atomicshop/wrappers/nodejsw/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
221
221
|
atomicshop/wrappers/nodejsw/install_nodejs.py,sha256=QZg-R2iTQt7kFb8wNtnTmwraSGwvUs34JIasdbNa7ZU,5154
|
|
222
222
|
atomicshop/wrappers/playwrightw/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
@@ -251,8 +251,8 @@ atomicshop/wrappers/socketw/socket_server_tester.py,sha256=AhpurHJmP2kgzHaUbq5ey
|
|
|
251
251
|
atomicshop/wrappers/socketw/socket_wrapper.py,sha256=aXBwlEIJhFT0-c4i8iNlFx2It9VpCEpsv--5Oqcpxao,11624
|
|
252
252
|
atomicshop/wrappers/socketw/ssl_base.py,sha256=k4V3gwkbq10MvOH4btU4onLX2GNOsSfUAdcHmL1rpVE,2274
|
|
253
253
|
atomicshop/wrappers/socketw/statistics_csv.py,sha256=t3dtDEfN47CfYVi0CW6Kc2QHTEeZVyYhc57IYYh5nmA,826
|
|
254
|
-
atomicshop-2.12.
|
|
255
|
-
atomicshop-2.12.
|
|
256
|
-
atomicshop-2.12.
|
|
257
|
-
atomicshop-2.12.
|
|
258
|
-
atomicshop-2.12.
|
|
254
|
+
atomicshop-2.12.17.dist-info/LICENSE.txt,sha256=lLU7EYycfYcK2NR_1gfnhnRC8b8ccOTElACYplgZN88,1094
|
|
255
|
+
atomicshop-2.12.17.dist-info/METADATA,sha256=eRzyeiQbRlaJQ62ckcewFJ7JdMmcSNBZKaVuhM4-GS8,10479
|
|
256
|
+
atomicshop-2.12.17.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
|
|
257
|
+
atomicshop-2.12.17.dist-info/top_level.txt,sha256=EgKJB-7xcrAPeqTRF2laD_Np2gNGYkJkd4OyXqpJphA,11
|
|
258
|
+
atomicshop-2.12.17.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|