malevich-coretools 0.2.17__tar.gz → 0.2.19__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.
Potentially problematic release.
This version of malevich-coretools might be problematic. Click here for more details.
- {malevich-coretools-0.2.17/malevich_coretools.egg-info → malevich-coretools-0.2.19}/PKG-INFO +1 -1
- malevich-coretools-0.2.19/VERSION +1 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/__init__.py +1 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/abstract/abstract.py +2 -2
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/config.py +1 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/helpers.py +53 -3
- malevich-coretools-0.2.19/malevich_coretools/secondary/kafka.py +32 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/utils.py +6 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19/malevich_coretools.egg-info}/PKG-INFO +1 -1
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/SOURCES.txt +1 -0
- malevich-coretools-0.2.17/VERSION +0 -1
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/LICENSE +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/MANIFEST.in +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/README.md +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/abstract/__init__.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/admin/__init__.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/admin/utils.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/funcs/__init__.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/funcs/funcs.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/funcs/helpers.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/__init__.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/const.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/tools/__init__.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/tools/vast.py +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/dependency_links.txt +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/requires.txt +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/top_level.txt +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/pyproject.toml +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/requirements.txt +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/setup.cfg +0 -0
- {malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/setup.py +0 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
0.2.19
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/helpers.py
RENAMED
|
@@ -1,15 +1,18 @@
|
|
|
1
1
|
import json
|
|
2
2
|
import random as rand
|
|
3
3
|
import string
|
|
4
|
-
from typing import Any, Callable, Dict, Tuple, Union
|
|
4
|
+
from typing import Any, Callable, Dict, Optional, Tuple, Union
|
|
5
5
|
|
|
6
6
|
from pydantic import BaseModel
|
|
7
7
|
|
|
8
8
|
from malevich_coretools.abstract.abstract import Alias, AppLogs, LogsResult
|
|
9
9
|
from malevich_coretools.secondary import Config
|
|
10
|
+
from malevich_coretools.secondary.kafka import handle_logs
|
|
10
11
|
|
|
11
12
|
__mini__delimiter = "-" * 25
|
|
12
13
|
__delimiter = "-" * 50
|
|
14
|
+
__colors = [f"\x1b[{i};20m" for i in range(31, 38)]
|
|
15
|
+
__color_reset = "\x1b[0m"
|
|
13
16
|
|
|
14
17
|
|
|
15
18
|
def to_json(data: Union[Dict[str, Any], Alias.Json], condition_and_msg: Tuple[Callable[[Dict[str, Any]], bool], str] = (lambda _: True, "")) -> str:
|
|
@@ -53,7 +56,7 @@ def __show_logs_result(res: LogsResult): # noqa: ANN202
|
|
|
53
56
|
print(logs)
|
|
54
57
|
|
|
55
58
|
|
|
56
|
-
def
|
|
59
|
+
def show_logs(app_logs: AppLogs, err: bool = False) -> None: # noqa: ANN202
|
|
57
60
|
show = Config.logger.error if err else Config.logger.info
|
|
58
61
|
show(f"operation_id = {app_logs.operationId}")
|
|
59
62
|
if app_logs.error is not None:
|
|
@@ -73,10 +76,51 @@ def __show_logs(app_logs: AppLogs, err: bool = False): # noqa: ANN202
|
|
|
73
76
|
print(__delimiter)
|
|
74
77
|
|
|
75
78
|
|
|
79
|
+
def show_logs_colored(app_logs: AppLogs, colors_dict: Optional[Dict[str, str]] = None) -> None:
|
|
80
|
+
"""colors_dict - should be unique for all app_logs by operation_id"""
|
|
81
|
+
def format(log, color: Optional[str]) -> None:
|
|
82
|
+
if color is None:
|
|
83
|
+
Config.logger.warning(log)
|
|
84
|
+
else:
|
|
85
|
+
Config.logger.warning(color + log + __color_reset)
|
|
86
|
+
|
|
87
|
+
def get_color(name: str) -> str:
|
|
88
|
+
if colors_dict is None:
|
|
89
|
+
return None
|
|
90
|
+
color = colors_dict.get(name, None)
|
|
91
|
+
if color is None:
|
|
92
|
+
color = __colors[len(colors_dict) % len(__colors)]
|
|
93
|
+
colors_dict[name] = color
|
|
94
|
+
return color
|
|
95
|
+
|
|
96
|
+
if app_logs.error is not None:
|
|
97
|
+
format(f"error: {app_logs.error}", get_color("error"))
|
|
98
|
+
if len(app_logs.dagLogs) > 0:
|
|
99
|
+
color = get_color("dagLogs")
|
|
100
|
+
for line in app_logs.dagLogs.splitlines():
|
|
101
|
+
format(f"dag: {line}", color)
|
|
102
|
+
for app_name, app_log in app_logs.data.items():
|
|
103
|
+
color = get_color(f"${app_name}")
|
|
104
|
+
for i, logs_result in enumerate(app_log.data):
|
|
105
|
+
app_name_prefix = f"{app_name}${i}" if i != 0 else app_name
|
|
106
|
+
if len(logs_result.data) > 0:
|
|
107
|
+
for line in logs_result.data.splitlines():
|
|
108
|
+
format(f"{app_name_prefix}$main: {line}", color)
|
|
109
|
+
if len(logs_result.logs) > 0:
|
|
110
|
+
for run_id, logs in logs_result.logs.items():
|
|
111
|
+
user_logs = logs_result.userLogs.get(run_id, "")
|
|
112
|
+
if len(user_logs) > 0:
|
|
113
|
+
for line in user_logs.splitlines():
|
|
114
|
+
format(f"{app_name_prefix}${run_id}: {line}", color)
|
|
115
|
+
if len(logs) > 0:
|
|
116
|
+
for line in logs.splitlines():
|
|
117
|
+
format(f"{app_name_prefix}${run_id}: {line}", color)
|
|
118
|
+
|
|
119
|
+
|
|
76
120
|
def show_logs_func(data: str, err: bool = False): # noqa: ANN201
|
|
77
121
|
try:
|
|
78
122
|
app_logs = AppLogs.parse_raw(data)
|
|
79
|
-
|
|
123
|
+
show_logs(app_logs, err=err)
|
|
80
124
|
except BaseException:
|
|
81
125
|
Config.logger.error("decode logs failed")
|
|
82
126
|
show = Config.logger.error if err else Config.logger.info
|
|
@@ -92,3 +136,9 @@ def show_fail_app_info(data: str, err: bool): # noqa: ANN201
|
|
|
92
136
|
except BaseException:
|
|
93
137
|
Config.logger.error("decode unsuccessful app_info fail")
|
|
94
138
|
print(data)
|
|
139
|
+
|
|
140
|
+
|
|
141
|
+
def logs_streaming(operation_id: str, kafka_host_port: Optional[str] = None, app_logs_show: Callable[[AppLogs], None] = show_logs_colored) -> None:
|
|
142
|
+
colors_dict = {}
|
|
143
|
+
for appLogs in handle_logs(operation_id, kafka_host_port=kafka_host_port):
|
|
144
|
+
app_logs_show(appLogs, colors_dict=colors_dict)
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
from typing import Generator, Optional
|
|
2
|
+
|
|
3
|
+
from kafka import KafkaConsumer
|
|
4
|
+
|
|
5
|
+
from malevich_coretools.abstract import AppLogs
|
|
6
|
+
from malevich_coretools.secondary import Config
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
def __logs_topic(operation_id: str) -> str:
|
|
10
|
+
return f"{operation_id}-logs"
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
def handle_logs(operation_id: str, kafka_host_port: Optional[str] = None) -> Generator[AppLogs, None, None]:
|
|
14
|
+
if kafka_host_port is None:
|
|
15
|
+
kafka_host_port = Config.KAFKA_HOST_PORT
|
|
16
|
+
assert kafka_host_port is not None, "kafka_host_port not set"
|
|
17
|
+
|
|
18
|
+
topic = __logs_topic(operation_id)
|
|
19
|
+
consumer = KafkaConsumer(topic, bootstrap_servers=kafka_host_port)
|
|
20
|
+
|
|
21
|
+
try:
|
|
22
|
+
for message in consumer:
|
|
23
|
+
if message.value == b'end':
|
|
24
|
+
return
|
|
25
|
+
try:
|
|
26
|
+
logs = AppLogs.model_validate_json(message.value)
|
|
27
|
+
except BaseException as ex:
|
|
28
|
+
Config.logger.error(message.value)
|
|
29
|
+
raise ex
|
|
30
|
+
yield logs
|
|
31
|
+
except KeyboardInterrupt:
|
|
32
|
+
pass
|
|
@@ -29,6 +29,12 @@ def set_host_port(host_port: str) -> None:
|
|
|
29
29
|
Config.HOST_PORT = host_port
|
|
30
30
|
|
|
31
31
|
|
|
32
|
+
def set_kafka_host_port(host_port: str) -> None:
|
|
33
|
+
"""update kafka host and port for malevich-kafka, example: `localhost:9092` """
|
|
34
|
+
assert len(host_port) > 0, "empty host port"
|
|
35
|
+
Config.KAFKA_HOST_PORT = host_port
|
|
36
|
+
|
|
37
|
+
|
|
32
38
|
def set_conn_url(conn_url: str) -> None:
|
|
33
39
|
"""analogue set_host_port; update `conn_url` for malevich-core, example: `http://localhost:8080/` """
|
|
34
40
|
set_host_port(conn_url)
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/SOURCES.txt
RENAMED
|
@@ -23,5 +23,6 @@ malevich_coretools/secondary/__init__.py
|
|
|
23
23
|
malevich_coretools/secondary/config.py
|
|
24
24
|
malevich_coretools/secondary/const.py
|
|
25
25
|
malevich_coretools/secondary/helpers.py
|
|
26
|
+
malevich_coretools/secondary/kafka.py
|
|
26
27
|
malevich_coretools/tools/__init__.py
|
|
27
28
|
malevich_coretools/tools/vast.py
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
0.2.17
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/abstract/__init__.py
RENAMED
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/admin/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/funcs/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/__init__.py
RENAMED
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/secondary/const.py
RENAMED
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools/tools/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/requires.txt
RENAMED
|
File without changes
|
{malevich-coretools-0.2.17 → malevich-coretools-0.2.19}/malevich_coretools.egg-info/top_level.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|