wizata-dsapi 2.0.0.dev7__tar.gz → 2.0.0.dev9__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.
- {wizata_dsapi-2.0.0.dev7/wizata_dsapi.egg-info → wizata_dsapi-2.0.0.dev9}/PKG-INFO +1 -1
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/__init__.py +3 -1
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/edge_device.py +15 -1
- wizata_dsapi-2.0.0.dev9/wizata_dsapi/edge_module.py +115 -0
- wizata_dsapi-2.0.0.dev9/wizata_dsapi/graylog_log.py +132 -0
- wizata_dsapi-2.0.0.dev9/wizata_dsapi/version.py +1 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9/wizata_dsapi.egg-info}/PKG-INFO +1 -1
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi.egg-info/SOURCES.txt +2 -0
- wizata_dsapi-2.0.0.dev7/wizata_dsapi/version.py +0 -1
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/LICENSE.txt +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/README.rst +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/setup.cfg +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/setup.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/api_config.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/api_dto.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/api_interface.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/bucket.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/business_label.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/context.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/dashboard.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/dataframe_toolkit.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/datapoint.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/datastore.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/ds_dataframe.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/dsapi_json_encoder.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/evaluation.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/execution.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/execution_log.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/experiment.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/group_system.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/ilogger.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/insight.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/mlmodel.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/mobile_asset.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/model_toolkit.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/models/__init__.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/models/common.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/notification.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/paged_query_result.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/pipeline.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/pipeline_image.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/plot.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/plots/__init__.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/plots/common.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/request.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/script.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/scripts/__init__.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/scripts/common.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/search.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/solution_component.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/streamlit_utils.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/template.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/trigger.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/twin.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/twinregistration.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/wizard_function.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/wizard_request.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/wizata_dsapi_client.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi/words.py +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi.egg-info/dependency_links.txt +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi.egg-info/requires.txt +0 -0
- {wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi.egg-info/top_level.txt +0 -0
|
@@ -52,5 +52,7 @@ from .streamlit_utils import (get_streamlit_token, get_streamlit_domain, get_str
|
|
|
52
52
|
from .search import FilterOperator, SearchQuery, SortOption, GroupSearchQuery
|
|
53
53
|
from .notification import NotificationScope, DeviceToken, AlertRule, AlertActive, MonitoredDatapoint
|
|
54
54
|
from .edge_device import EdgeDevice, EdgeDeviceStatus, EdgeDeviceType
|
|
55
|
+
from .edge_module import EdgeModule, EdgeModuleType, WIZATA_MODULES
|
|
55
56
|
from .dashboard import Dashboard, DashboardType
|
|
56
|
-
from .mobile_asset import MobileAssetTile, MobileAssetTileType, MobileAssetConfig
|
|
57
|
+
from .mobile_asset import MobileAssetTile, MobileAssetTileType, MobileAssetConfig
|
|
58
|
+
from .graylog_log import GraylogLog
|
|
@@ -35,6 +35,8 @@ class EdgeDevice(ApiDto):
|
|
|
35
35
|
:ivar EdgeDeviceStatus status: current status of the device.
|
|
36
36
|
:ivar int status_code: numeric status code.
|
|
37
37
|
:ivar EdgeDeviceType device_type: type of the edge device.
|
|
38
|
+
:ivar str connection_state: IoT Hub connection state ('Connected' or 'Disconnected'), enriched from IoT Hub.
|
|
39
|
+
:ivar str last_activity_time: last device activity timestamp from IoT Hub.
|
|
38
40
|
"""
|
|
39
41
|
|
|
40
42
|
@classmethod
|
|
@@ -55,7 +57,9 @@ class EdgeDevice(ApiDto):
|
|
|
55
57
|
twin_id: uuid.UUID = None,
|
|
56
58
|
status: EdgeDeviceStatus = None,
|
|
57
59
|
status_code: int = None,
|
|
58
|
-
device_type: EdgeDeviceType = None
|
|
60
|
+
device_type: EdgeDeviceType = None,
|
|
61
|
+
connection_state: str = None,
|
|
62
|
+
last_activity_time: str = None):
|
|
59
63
|
if edge_device_id is None:
|
|
60
64
|
self.edge_device_id = uuid.uuid4()
|
|
61
65
|
else:
|
|
@@ -67,6 +71,8 @@ class EdgeDevice(ApiDto):
|
|
|
67
71
|
self.status = status
|
|
68
72
|
self.status_code = status_code
|
|
69
73
|
self.device_type = device_type
|
|
74
|
+
self.connection_state = connection_state
|
|
75
|
+
self.last_activity_time = last_activity_time
|
|
70
76
|
|
|
71
77
|
def api_id(self) -> str:
|
|
72
78
|
return str(self.edge_device_id).upper()
|
|
@@ -97,6 +103,10 @@ class EdgeDevice(ApiDto):
|
|
|
97
103
|
self.status_code = int(obj["statusCode"])
|
|
98
104
|
if "deviceType" in obj and obj["deviceType"] is not None:
|
|
99
105
|
self.device_type = EdgeDeviceType(obj["deviceType"])
|
|
106
|
+
if "connectionState" in obj and obj["connectionState"] is not None:
|
|
107
|
+
self.connection_state = obj["connectionState"]
|
|
108
|
+
if "lastActivityTime" in obj and obj["lastActivityTime"] is not None:
|
|
109
|
+
self.last_activity_time = obj["lastActivityTime"]
|
|
100
110
|
|
|
101
111
|
def to_json(self, target: str = None):
|
|
102
112
|
obj = {
|
|
@@ -116,4 +126,8 @@ class EdgeDevice(ApiDto):
|
|
|
116
126
|
obj["statusCode"] = self.status_code
|
|
117
127
|
if self.device_type is not None:
|
|
118
128
|
obj["deviceType"] = self.device_type.value
|
|
129
|
+
if self.connection_state is not None:
|
|
130
|
+
obj["connectionState"] = self.connection_state
|
|
131
|
+
if self.last_activity_time is not None:
|
|
132
|
+
obj["lastActivityTime"] = self.last_activity_time
|
|
119
133
|
return obj
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
from enum import Enum
|
|
2
|
+
from .api_dto import Dto
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
class EdgeModuleType(Enum):
|
|
6
|
+
"""
|
|
7
|
+
Classification of an edge module.
|
|
8
|
+
|
|
9
|
+
WIZATA: modules developed and maintained by Wizata (configsync, message_client, pipeline_runner).
|
|
10
|
+
SYSTEM: IoT Edge runtime and third-party infrastructure (edgeAgent, edgeHub, influxdb, rabbitmq, loki, ...).
|
|
11
|
+
"""
|
|
12
|
+
WIZATA = "wizata"
|
|
13
|
+
SYSTEM = "system"
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
# Hardcoded registry of known Wizata modules.
|
|
17
|
+
# Maps module_id to a human-readable description.
|
|
18
|
+
WIZATA_MODULES = {
|
|
19
|
+
"configsync": "Configuration synchronization between cloud and edge",
|
|
20
|
+
"message_client": "Message client for edge-to-cloud telemetry",
|
|
21
|
+
"pipeline_runner": "Pipeline execution engine on edge",
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def _extract_image_version(image: str) -> str:
|
|
26
|
+
"""Extract the tag portion after ':' from a container image reference."""
|
|
27
|
+
if image and ":" in image:
|
|
28
|
+
return image.rsplit(":", 1)[1]
|
|
29
|
+
return None
|
|
30
|
+
|
|
31
|
+
|
|
32
|
+
class EdgeModule(Dto):
|
|
33
|
+
"""
|
|
34
|
+
Represents a module deployed on an IoT Edge device.
|
|
35
|
+
|
|
36
|
+
:ivar str module_id: module identifier (e.g. 'configsync', '$edgeAgent').
|
|
37
|
+
:ivar str runtime_status: runtime status from $edgeAgent reported twin (e.g. 'running', 'stopped').
|
|
38
|
+
:ivar int exit_code: last exit code of the module container.
|
|
39
|
+
:ivar str last_start_time: last container start time (UTC).
|
|
40
|
+
:ivar str last_exit_time: last container exit time (UTC).
|
|
41
|
+
:ivar str image: container image reference.
|
|
42
|
+
:ivar str image_version: tag extracted from image (e.g. 'p12-20260313.3'), only set for wizata modules.
|
|
43
|
+
:ivar str last_updated: when this module's status was last reported to IoT Hub (from $edgeAgent twin $metadata).
|
|
44
|
+
:ivar EdgeModuleType module_type: wizata or system classification.
|
|
45
|
+
"""
|
|
46
|
+
|
|
47
|
+
def __init__(self,
|
|
48
|
+
module_id: str = None,
|
|
49
|
+
runtime_status: str = None,
|
|
50
|
+
exit_code: int = None,
|
|
51
|
+
last_start_time: str = None,
|
|
52
|
+
last_exit_time: str = None,
|
|
53
|
+
image: str = None,
|
|
54
|
+
image_version: str = None,
|
|
55
|
+
last_updated: str = None,
|
|
56
|
+
module_type: EdgeModuleType = None):
|
|
57
|
+
self.module_id = module_id
|
|
58
|
+
self.runtime_status = runtime_status
|
|
59
|
+
self.exit_code = exit_code
|
|
60
|
+
self.last_start_time = last_start_time
|
|
61
|
+
self.last_exit_time = last_exit_time
|
|
62
|
+
self.image = image
|
|
63
|
+
self.last_updated = last_updated
|
|
64
|
+
if module_type is not None:
|
|
65
|
+
self.module_type = module_type
|
|
66
|
+
elif module_id is not None:
|
|
67
|
+
self.module_type = EdgeModuleType.WIZATA if module_id in WIZATA_MODULES else EdgeModuleType.SYSTEM
|
|
68
|
+
else:
|
|
69
|
+
self.module_type = None
|
|
70
|
+
# image_version: explicit value wins, otherwise extract for wizata modules only
|
|
71
|
+
if image_version is not None:
|
|
72
|
+
self.image_version = image_version
|
|
73
|
+
elif self.module_type == EdgeModuleType.WIZATA and image:
|
|
74
|
+
self.image_version = _extract_image_version(image)
|
|
75
|
+
else:
|
|
76
|
+
self.image_version = None
|
|
77
|
+
|
|
78
|
+
@classmethod
|
|
79
|
+
def from_dict(cls, data: dict) -> "EdgeModule":
|
|
80
|
+
module_type = None
|
|
81
|
+
if "moduleType" in data and data["moduleType"] is not None:
|
|
82
|
+
module_type = EdgeModuleType(data["moduleType"])
|
|
83
|
+
return cls(
|
|
84
|
+
module_id=data.get("moduleId"),
|
|
85
|
+
runtime_status=data.get("runtimeStatus"),
|
|
86
|
+
exit_code=data.get("exitCode"),
|
|
87
|
+
last_start_time=data.get("lastStartTime"),
|
|
88
|
+
last_exit_time=data.get("lastExitTime"),
|
|
89
|
+
image=data.get("image"),
|
|
90
|
+
image_version=data.get("imageVersion"),
|
|
91
|
+
last_updated=data.get("lastUpdated"),
|
|
92
|
+
module_type=module_type,
|
|
93
|
+
)
|
|
94
|
+
|
|
95
|
+
def to_dict(self) -> dict:
|
|
96
|
+
obj = {}
|
|
97
|
+
if self.module_id is not None:
|
|
98
|
+
obj["moduleId"] = self.module_id
|
|
99
|
+
if self.runtime_status is not None:
|
|
100
|
+
obj["runtimeStatus"] = self.runtime_status
|
|
101
|
+
if self.exit_code is not None:
|
|
102
|
+
obj["exitCode"] = self.exit_code
|
|
103
|
+
if self.last_start_time is not None:
|
|
104
|
+
obj["lastStartTime"] = self.last_start_time
|
|
105
|
+
if self.last_exit_time is not None:
|
|
106
|
+
obj["lastExitTime"] = self.last_exit_time
|
|
107
|
+
if self.image is not None:
|
|
108
|
+
obj["image"] = self.image
|
|
109
|
+
if self.image_version is not None:
|
|
110
|
+
obj["imageVersion"] = self.image_version
|
|
111
|
+
if self.last_updated is not None:
|
|
112
|
+
obj["lastUpdated"] = self.last_updated
|
|
113
|
+
if self.module_type is not None:
|
|
114
|
+
obj["moduleType"] = self.module_type.value
|
|
115
|
+
return obj
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
from typing import Optional
|
|
2
|
+
from datetime import datetime, timezone
|
|
3
|
+
|
|
4
|
+
|
|
5
|
+
class GraylogLog:
|
|
6
|
+
"""
|
|
7
|
+
DTO for a single Graylog log entry.
|
|
8
|
+
|
|
9
|
+
Represents a log message from Graylog with standard GELF fields
|
|
10
|
+
plus Wizata custom fields (appId, edgeDeviceId, etc.).
|
|
11
|
+
|
|
12
|
+
Timestamps are always milliseconds (int) in serialized form.
|
|
13
|
+
|
|
14
|
+
:ivar int timestamp: event timestamp in milliseconds
|
|
15
|
+
:ivar str message: log message text
|
|
16
|
+
:ivar int level: syslog severity level (0=Emergency .. 7=Debug)
|
|
17
|
+
:ivar str source: source hostname
|
|
18
|
+
:ivar str app_id: application identifier
|
|
19
|
+
:ivar str edge_device_id: IoT Edge device identifier
|
|
20
|
+
:ivar str env: environment name
|
|
21
|
+
:ivar str tenant_id: tenant identifier
|
|
22
|
+
:ivar dict extra: any additional fields from the Graylog message
|
|
23
|
+
"""
|
|
24
|
+
|
|
25
|
+
@classmethod
|
|
26
|
+
def from_dict(cls, data: dict) -> "GraylogLog":
|
|
27
|
+
"""
|
|
28
|
+
Deserialize a Graylog message dict into a GraylogLog.
|
|
29
|
+
|
|
30
|
+
Graylog returns timestamps as ISO 8601 strings — these are
|
|
31
|
+
converted to millisecond timestamps.
|
|
32
|
+
|
|
33
|
+
:param data: Graylog message dict (from API response message field).
|
|
34
|
+
"""
|
|
35
|
+
timestamp = data.get("timestamp")
|
|
36
|
+
timestamp_ms = None
|
|
37
|
+
if timestamp is not None:
|
|
38
|
+
if isinstance(timestamp, (int, float)):
|
|
39
|
+
timestamp_ms = int(timestamp)
|
|
40
|
+
elif isinstance(timestamp, str):
|
|
41
|
+
timestamp_ms = cls._parse_graylog_timestamp(timestamp)
|
|
42
|
+
|
|
43
|
+
known_fields = {
|
|
44
|
+
"timestamp", "message", "level", "source",
|
|
45
|
+
"appId", "app_id",
|
|
46
|
+
"edgeDeviceId", "edge_device_id",
|
|
47
|
+
"env", "tenantId", "tenant_id",
|
|
48
|
+
"gl2_message_id", "gl2_remote_ip", "gl2_remote_port",
|
|
49
|
+
"gl2_source_input", "gl2_source_node",
|
|
50
|
+
"streams", "_id", "facility",
|
|
51
|
+
}
|
|
52
|
+
extra = {k: v for k, v in data.items() if k not in known_fields}
|
|
53
|
+
|
|
54
|
+
return cls(
|
|
55
|
+
timestamp=timestamp_ms,
|
|
56
|
+
message=data.get("message"),
|
|
57
|
+
level=int(data["level"]) if "level" in data and data["level"] is not None else None,
|
|
58
|
+
source=data.get("source"),
|
|
59
|
+
app_id=data.get("appId") or data.get("app_id"),
|
|
60
|
+
edge_device_id=data.get("edgeDeviceId") or data.get("edge_device_id"),
|
|
61
|
+
env=data.get("env"),
|
|
62
|
+
tenant_id=data.get("tenantId") or data.get("tenant_id"),
|
|
63
|
+
extra=extra if extra else None,
|
|
64
|
+
)
|
|
65
|
+
|
|
66
|
+
def __init__(self,
|
|
67
|
+
timestamp: Optional[int] = None,
|
|
68
|
+
message: Optional[str] = None,
|
|
69
|
+
level: Optional[int] = None,
|
|
70
|
+
source: Optional[str] = None,
|
|
71
|
+
app_id: Optional[str] = None,
|
|
72
|
+
edge_device_id: Optional[str] = None,
|
|
73
|
+
env: Optional[str] = None,
|
|
74
|
+
tenant_id: Optional[str] = None,
|
|
75
|
+
extra: Optional[dict] = None):
|
|
76
|
+
self.timestamp = timestamp
|
|
77
|
+
self.message = message
|
|
78
|
+
self.level = level
|
|
79
|
+
self.source = source
|
|
80
|
+
self.app_id = app_id
|
|
81
|
+
self.edge_device_id = edge_device_id
|
|
82
|
+
self.env = env
|
|
83
|
+
self.tenant_id = tenant_id
|
|
84
|
+
self.extra = extra or {}
|
|
85
|
+
|
|
86
|
+
def to_dict(self) -> dict:
|
|
87
|
+
"""
|
|
88
|
+
Serialize to a camelCase dict.
|
|
89
|
+
Timestamps are millisecond integers.
|
|
90
|
+
"""
|
|
91
|
+
data = {}
|
|
92
|
+
if self.timestamp is not None:
|
|
93
|
+
data["timestamp"] = self.timestamp
|
|
94
|
+
if self.message is not None:
|
|
95
|
+
data["message"] = self.message
|
|
96
|
+
if self.level is not None:
|
|
97
|
+
data["level"] = self.level
|
|
98
|
+
if self.source is not None:
|
|
99
|
+
data["source"] = self.source
|
|
100
|
+
if self.app_id is not None:
|
|
101
|
+
data["appId"] = self.app_id
|
|
102
|
+
if self.edge_device_id is not None:
|
|
103
|
+
data["edgeDeviceId"] = self.edge_device_id
|
|
104
|
+
if self.env is not None:
|
|
105
|
+
data["env"] = self.env
|
|
106
|
+
if self.tenant_id is not None:
|
|
107
|
+
data["tenantId"] = self.tenant_id
|
|
108
|
+
if self.extra:
|
|
109
|
+
data.update(self.extra)
|
|
110
|
+
return data
|
|
111
|
+
|
|
112
|
+
@staticmethod
|
|
113
|
+
def _parse_graylog_timestamp(ts_str: str) -> Optional[int]:
|
|
114
|
+
"""
|
|
115
|
+
Parse a Graylog ISO 8601 timestamp string to milliseconds.
|
|
116
|
+
Graylog format: '2024-01-15T10:30:00.123Z' or '2024-01-15 10:30:00.123'
|
|
117
|
+
"""
|
|
118
|
+
formats = [
|
|
119
|
+
"%Y-%m-%dT%H:%M:%S.%fZ",
|
|
120
|
+
"%Y-%m-%dT%H:%M:%SZ",
|
|
121
|
+
"%Y-%m-%dT%H:%M:%S.%f",
|
|
122
|
+
"%Y-%m-%dT%H:%M:%S",
|
|
123
|
+
"%Y-%m-%d %H:%M:%S.%f",
|
|
124
|
+
"%Y-%m-%d %H:%M:%S",
|
|
125
|
+
]
|
|
126
|
+
for fmt in formats:
|
|
127
|
+
try:
|
|
128
|
+
dt = datetime.strptime(ts_str, fmt).replace(tzinfo=timezone.utc)
|
|
129
|
+
return int(dt.timestamp() * 1000)
|
|
130
|
+
except ValueError:
|
|
131
|
+
continue
|
|
132
|
+
return None
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
__version__ = "2.0.0.dev9"
|
|
@@ -15,10 +15,12 @@ wizata_dsapi/datastore.py
|
|
|
15
15
|
wizata_dsapi/ds_dataframe.py
|
|
16
16
|
wizata_dsapi/dsapi_json_encoder.py
|
|
17
17
|
wizata_dsapi/edge_device.py
|
|
18
|
+
wizata_dsapi/edge_module.py
|
|
18
19
|
wizata_dsapi/evaluation.py
|
|
19
20
|
wizata_dsapi/execution.py
|
|
20
21
|
wizata_dsapi/execution_log.py
|
|
21
22
|
wizata_dsapi/experiment.py
|
|
23
|
+
wizata_dsapi/graylog_log.py
|
|
22
24
|
wizata_dsapi/group_system.py
|
|
23
25
|
wizata_dsapi/ilogger.py
|
|
24
26
|
wizata_dsapi/insight.py
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
__version__ = "2.0.0.dev7"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{wizata_dsapi-2.0.0.dev7 → wizata_dsapi-2.0.0.dev9}/wizata_dsapi.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|