logdash 0.1.0__tar.gz → 0.2.0__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.
- {logdash-0.1.0 → logdash-0.2.0}/LICENSE +1 -1
- logdash-0.2.0/PKG-INFO +109 -0
- logdash-0.2.0/README.md +72 -0
- logdash-0.2.0/examples/basic_usage.py +49 -0
- logdash-0.2.0/logdash/__init__.py +12 -0
- logdash-0.2.0/logdash/constants.py +33 -0
- logdash-0.2.0/logdash/core.py +73 -0
- logdash-0.2.0/logdash/internal.py +6 -0
- logdash-0.2.0/logdash/logger.py +96 -0
- logdash-0.2.0/logdash/metrics/__init__.py +8 -0
- logdash-0.2.0/logdash/metrics/base.py +29 -0
- logdash-0.2.0/logdash/metrics/factory.py +29 -0
- logdash-0.2.0/logdash/metrics/impl.py +85 -0
- logdash-0.2.0/logdash/metrics/noop.py +32 -0
- logdash-0.2.0/logdash/sync/__init__.py +7 -0
- logdash-0.2.0/logdash/sync/base.py +21 -0
- logdash-0.2.0/logdash/sync/factory.py +29 -0
- logdash-0.2.0/logdash/sync/http.py +66 -0
- logdash-0.2.0/logdash/sync/noop.py +24 -0
- logdash-0.2.0/logdash.egg-info/PKG-INFO +109 -0
- logdash-0.2.0/logdash.egg-info/SOURCES.txt +25 -0
- logdash-0.2.0/logdash.egg-info/requires.txt +2 -0
- logdash-0.2.0/setup.py +37 -0
- logdash-0.1.0/PKG-INFO +0 -24
- logdash-0.1.0/README.md +0 -60
- logdash-0.1.0/logdash/__init__.py +0 -5
- logdash-0.1.0/logdash/logdash.py +0 -43
- logdash-0.1.0/logdash/logger/__init__.py +0 -1
- logdash-0.1.0/logdash/logger/internal_logger.py +0 -11
- logdash-0.1.0/logdash/logger/logger.py +0 -66
- logdash-0.1.0/logdash/metrics/__init__.py +0 -1
- logdash-0.1.0/logdash/metrics/base_metrics.py +0 -11
- logdash-0.1.0/logdash/metrics/create_metrics.py +0 -15
- logdash-0.1.0/logdash/metrics/metrics.py +0 -50
- logdash-0.1.0/logdash/metrics/noop_metrics.py +0 -9
- logdash-0.1.0/logdash/sync/__init__.py +0 -1
- logdash-0.1.0/logdash/sync/create_log_sync.py +0 -15
- logdash-0.1.0/logdash/sync/http_log_sync.py +0 -31
- logdash-0.1.0/logdash/sync/log_sync.py +0 -9
- logdash-0.1.0/logdash/sync/noop_log_sync.py +0 -7
- logdash-0.1.0/logdash/types/__init__.py +0 -1
- logdash-0.1.0/logdash/types/initialization_params.py +0 -16
- logdash-0.1.0/logdash/types/log_level.py +0 -11
- logdash-0.1.0/logdash.egg-info/PKG-INFO +0 -24
- logdash-0.1.0/logdash.egg-info/SOURCES.txt +0 -27
- logdash-0.1.0/logdash.egg-info/requires.txt +0 -2
- logdash-0.1.0/setup.py +0 -22
- {logdash-0.1.0 → logdash-0.2.0}/MANIFEST.in +0 -0
- {logdash-0.1.0 → logdash-0.2.0}/logdash.egg-info/dependency_links.txt +0 -0
- {logdash-0.1.0 → logdash-0.2.0}/logdash.egg-info/top_level.txt +0 -0
- {logdash-0.1.0 → logdash-0.2.0}/setup.cfg +0 -0
logdash-0.2.0/PKG-INFO
ADDED
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: logdash
|
|
3
|
+
Version: 0.2.0
|
|
4
|
+
Summary: Python SDK for logdash logging and metrics service
|
|
5
|
+
Home-page: https://logdash.io
|
|
6
|
+
Author: logdash
|
|
7
|
+
Author-email: info@logdash.io
|
|
8
|
+
Keywords: logging,metrics,monitoring
|
|
9
|
+
Classifier: Development Status :: 4 - Beta
|
|
10
|
+
Classifier: Intended Audience :: Developers
|
|
11
|
+
Classifier: Programming Language :: Python :: 3
|
|
12
|
+
Classifier: Programming Language :: Python :: 3.7
|
|
13
|
+
Classifier: Programming Language :: Python :: 3.8
|
|
14
|
+
Classifier: Programming Language :: Python :: 3.9
|
|
15
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
16
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
17
|
+
Classifier: Operating System :: OS Independent
|
|
18
|
+
Classifier: Topic :: Software Development :: Libraries :: Python Modules
|
|
19
|
+
Classifier: Topic :: System :: Logging
|
|
20
|
+
Classifier: Topic :: System :: Monitoring
|
|
21
|
+
Requires-Python: >=3.7
|
|
22
|
+
Description-Content-Type: text/markdown
|
|
23
|
+
License-File: LICENSE
|
|
24
|
+
Requires-Dist: requests>=2.25.0
|
|
25
|
+
Requires-Dist: colorama>=0.4.4
|
|
26
|
+
Dynamic: author
|
|
27
|
+
Dynamic: author-email
|
|
28
|
+
Dynamic: classifier
|
|
29
|
+
Dynamic: description
|
|
30
|
+
Dynamic: description-content-type
|
|
31
|
+
Dynamic: home-page
|
|
32
|
+
Dynamic: keywords
|
|
33
|
+
Dynamic: license-file
|
|
34
|
+
Dynamic: requires-dist
|
|
35
|
+
Dynamic: requires-python
|
|
36
|
+
Dynamic: summary
|
|
37
|
+
|
|
38
|
+
# logdash - Python SDK
|
|
39
|
+
|
|
40
|
+
Logdash is a zero-config observability platform. This package serves as a Python interface to use it.
|
|
41
|
+
|
|
42
|
+
## Pre-requisites
|
|
43
|
+
|
|
44
|
+
Setup your free project in less than 2 minutes at [logdash.io](https://logdash.io/)
|
|
45
|
+
|
|
46
|
+
## Installation
|
|
47
|
+
|
|
48
|
+
```bash
|
|
49
|
+
pip install logdash
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
## Logging
|
|
53
|
+
|
|
54
|
+
```python
|
|
55
|
+
from logdash import create_logdash
|
|
56
|
+
|
|
57
|
+
# Initialize with your API key
|
|
58
|
+
logdash = create_logdash({
|
|
59
|
+
# optional, but recommended to see your logs in the dashboard
|
|
60
|
+
"api_key": "<your-api-key>",
|
|
61
|
+
})
|
|
62
|
+
|
|
63
|
+
# Access the logger
|
|
64
|
+
logger = logdash.logger
|
|
65
|
+
|
|
66
|
+
logger.info("Application started successfully")
|
|
67
|
+
logger.error("An unexpected error occurred")
|
|
68
|
+
logger.warn("Low disk space warning")
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
## Metrics
|
|
72
|
+
|
|
73
|
+
```python
|
|
74
|
+
from logdash import create_logdash
|
|
75
|
+
|
|
76
|
+
# Initialize with your API key
|
|
77
|
+
logdash = create_logdash({
|
|
78
|
+
# optional, but recommended as metrics are only hosted remotely
|
|
79
|
+
"api_key": "<your-api-key>",
|
|
80
|
+
})
|
|
81
|
+
|
|
82
|
+
# Access metrics
|
|
83
|
+
metrics = logdash.metrics
|
|
84
|
+
|
|
85
|
+
# to set absolute value
|
|
86
|
+
metrics.set("users", 0)
|
|
87
|
+
|
|
88
|
+
# to modify existing metric
|
|
89
|
+
metrics.mutate("users", 1)
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
## View
|
|
93
|
+
|
|
94
|
+
To see the logs or metrics, go to your project dashboard
|
|
95
|
+
|
|
96
|
+

|
|
97
|
+

|
|
98
|
+
|
|
99
|
+
## License
|
|
100
|
+
|
|
101
|
+
This project is licensed under the MIT License.
|
|
102
|
+
|
|
103
|
+
## Contributing
|
|
104
|
+
|
|
105
|
+
Contributions are welcome! Feel free to open issues or submit pull requests.
|
|
106
|
+
|
|
107
|
+
## Support
|
|
108
|
+
|
|
109
|
+
If you encounter any issues, please open an issue on GitHub or let us know at [contact@logdash.io](mailto:contact@logdash.io).
|
logdash-0.2.0/README.md
ADDED
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
# logdash - Python SDK
|
|
2
|
+
|
|
3
|
+
Logdash is a zero-config observability platform. This package serves as a Python interface to use it.
|
|
4
|
+
|
|
5
|
+
## Pre-requisites
|
|
6
|
+
|
|
7
|
+
Setup your free project in less than 2 minutes at [logdash.io](https://logdash.io/)
|
|
8
|
+
|
|
9
|
+
## Installation
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
pip install logdash
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
## Logging
|
|
16
|
+
|
|
17
|
+
```python
|
|
18
|
+
from logdash import create_logdash
|
|
19
|
+
|
|
20
|
+
# Initialize with your API key
|
|
21
|
+
logdash = create_logdash({
|
|
22
|
+
# optional, but recommended to see your logs in the dashboard
|
|
23
|
+
"api_key": "<your-api-key>",
|
|
24
|
+
})
|
|
25
|
+
|
|
26
|
+
# Access the logger
|
|
27
|
+
logger = logdash.logger
|
|
28
|
+
|
|
29
|
+
logger.info("Application started successfully")
|
|
30
|
+
logger.error("An unexpected error occurred")
|
|
31
|
+
logger.warn("Low disk space warning")
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
## Metrics
|
|
35
|
+
|
|
36
|
+
```python
|
|
37
|
+
from logdash import create_logdash
|
|
38
|
+
|
|
39
|
+
# Initialize with your API key
|
|
40
|
+
logdash = create_logdash({
|
|
41
|
+
# optional, but recommended as metrics are only hosted remotely
|
|
42
|
+
"api_key": "<your-api-key>",
|
|
43
|
+
})
|
|
44
|
+
|
|
45
|
+
# Access metrics
|
|
46
|
+
metrics = logdash.metrics
|
|
47
|
+
|
|
48
|
+
# to set absolute value
|
|
49
|
+
metrics.set("users", 0)
|
|
50
|
+
|
|
51
|
+
# to modify existing metric
|
|
52
|
+
metrics.mutate("users", 1)
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
## View
|
|
56
|
+
|
|
57
|
+
To see the logs or metrics, go to your project dashboard
|
|
58
|
+
|
|
59
|
+

|
|
60
|
+

|
|
61
|
+
|
|
62
|
+
## License
|
|
63
|
+
|
|
64
|
+
This project is licensed under the MIT License.
|
|
65
|
+
|
|
66
|
+
## Contributing
|
|
67
|
+
|
|
68
|
+
Contributions are welcome! Feel free to open issues or submit pull requests.
|
|
69
|
+
|
|
70
|
+
## Support
|
|
71
|
+
|
|
72
|
+
If you encounter any issues, please open an issue on GitHub or let us know at [contact@logdash.io](mailto:contact@logdash.io).
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
"""
|
|
3
|
+
Basic usage example for the logdash SDK.
|
|
4
|
+
"""
|
|
5
|
+
|
|
6
|
+
import time
|
|
7
|
+
from logdash import create_logdash
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def main():
|
|
11
|
+
"""Main function demonstrating logdash usage."""
|
|
12
|
+
# Initialize logdash with your API key
|
|
13
|
+
# For testing without an API key, logs will only be printed locally
|
|
14
|
+
logdash = create_logdash({
|
|
15
|
+
"api_key": "your-api-key", # Replace with your actual API key
|
|
16
|
+
"host": "https://api.logdash.io",
|
|
17
|
+
"verbose": True, # Enable verbose mode for development
|
|
18
|
+
})
|
|
19
|
+
|
|
20
|
+
# Get the logger instance
|
|
21
|
+
logger = logdash.logger
|
|
22
|
+
|
|
23
|
+
# Get the metrics instance
|
|
24
|
+
metrics = logdash.metrics
|
|
25
|
+
|
|
26
|
+
# Log messages at different levels
|
|
27
|
+
logger.info("Application started")
|
|
28
|
+
logger.debug("Debug information")
|
|
29
|
+
logger.warn("Warning message")
|
|
30
|
+
logger.error("Error occurred")
|
|
31
|
+
logger.http("HTTP request processed")
|
|
32
|
+
logger.verbose("Verbose details")
|
|
33
|
+
|
|
34
|
+
# Track metrics
|
|
35
|
+
for i in range(5):
|
|
36
|
+
# Set absolute values
|
|
37
|
+
metrics.set("active_users", 100 + i * 10)
|
|
38
|
+
|
|
39
|
+
# Mutate values (increment/decrement)
|
|
40
|
+
metrics.mutate("requests_count", 1)
|
|
41
|
+
|
|
42
|
+
logger.info(f"Iteration {i+1}/5 completed")
|
|
43
|
+
time.sleep(1)
|
|
44
|
+
|
|
45
|
+
logger.info("Example completed")
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
if __name__ == "__main__":
|
|
49
|
+
main()
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
"""
|
|
2
|
+
logdash Python SDK for logging and metrics.
|
|
3
|
+
|
|
4
|
+
This package provides utilities for logging and metrics collection.
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
from logdash.core import create_logdash
|
|
8
|
+
from logdash.logger import Logger
|
|
9
|
+
from logdash.metrics import MetricOperation
|
|
10
|
+
|
|
11
|
+
__all__ = ["create_logdash", "Logger", "MetricOperation"]
|
|
12
|
+
__version__ = "0.2.0"
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
"""Constants used throughout the logdash SDK."""
|
|
2
|
+
|
|
3
|
+
from enum import Enum
|
|
4
|
+
from colorama import Fore
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
class LogLevel(str, Enum):
|
|
8
|
+
"""Log levels supported by logdash."""
|
|
9
|
+
ERROR = "error"
|
|
10
|
+
WARN = "warning"
|
|
11
|
+
INFO = "info"
|
|
12
|
+
HTTP = "http"
|
|
13
|
+
VERBOSE = "verbose"
|
|
14
|
+
DEBUG = "debug"
|
|
15
|
+
SILLY = "silly"
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
class MetricOperation(str, Enum):
|
|
19
|
+
"""Metric operations supported by logdash."""
|
|
20
|
+
SET = "set"
|
|
21
|
+
CHANGE = "change"
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
# Color mapping for log levels in terminal output
|
|
25
|
+
LOG_LEVEL_COLORS = {
|
|
26
|
+
LogLevel.ERROR: Fore.RED,
|
|
27
|
+
LogLevel.WARN: Fore.YELLOW,
|
|
28
|
+
LogLevel.INFO: Fore.BLUE,
|
|
29
|
+
LogLevel.HTTP: Fore.CYAN,
|
|
30
|
+
LogLevel.VERBOSE: Fore.GREEN,
|
|
31
|
+
LogLevel.DEBUG: Fore.LIGHTGREEN_EX,
|
|
32
|
+
LogLevel.SILLY: Fore.LIGHTBLACK_EX,
|
|
33
|
+
}
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
"""Core functionality for the logdash SDK."""
|
|
2
|
+
|
|
3
|
+
from datetime import datetime
|
|
4
|
+
from typing import Dict, Optional, Any
|
|
5
|
+
|
|
6
|
+
from logdash.logger import Logger
|
|
7
|
+
from logdash.metrics.base import BaseMetrics
|
|
8
|
+
from logdash.metrics.factory import create_metrics
|
|
9
|
+
from logdash.sync.factory import create_log_sync
|
|
10
|
+
from logdash.constants import LogLevel
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
class logdash:
|
|
14
|
+
def __init__(self, api_key: Optional[str] = None, host: str = "https://api.logdash.io", verbose: bool = False):
|
|
15
|
+
"""
|
|
16
|
+
Initialize a new logdash instance.
|
|
17
|
+
|
|
18
|
+
Args:
|
|
19
|
+
api_key: Your logdash API key
|
|
20
|
+
host: logdash API host (defaults to https://api.logdash.io)
|
|
21
|
+
verbose: Enable verbose mode
|
|
22
|
+
"""
|
|
23
|
+
# Ensure we have an API key (or empty string)
|
|
24
|
+
self._api_key = api_key or ""
|
|
25
|
+
self._host = host
|
|
26
|
+
self._verbose = verbose
|
|
27
|
+
|
|
28
|
+
# Create log sync and metrics instances
|
|
29
|
+
self._log_sync = create_log_sync(self._api_key, self._host, self._verbose)
|
|
30
|
+
self._metrics_instance = create_metrics(self._api_key, self._host, self._verbose)
|
|
31
|
+
|
|
32
|
+
# Initialize logger
|
|
33
|
+
def on_log(level: LogLevel, message: str) -> None:
|
|
34
|
+
self._log_sync.send(message, level, datetime.now().isoformat())
|
|
35
|
+
|
|
36
|
+
self._logger_instance = Logger(log_method=print, on_log=on_log)
|
|
37
|
+
|
|
38
|
+
@property
|
|
39
|
+
def logger(self) -> Logger:
|
|
40
|
+
"""Get the logger instance."""
|
|
41
|
+
return self._logger_instance
|
|
42
|
+
|
|
43
|
+
@property
|
|
44
|
+
def metrics(self) -> BaseMetrics:
|
|
45
|
+
"""Get the metrics instance."""
|
|
46
|
+
return self._metrics_instance
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def create_logdash(params: Optional[Dict[str, Any]] = None) -> logdash:
|
|
50
|
+
"""
|
|
51
|
+
Create a new logdash instance with logger and metrics.
|
|
52
|
+
|
|
53
|
+
Args:
|
|
54
|
+
params: Optional dictionary with configuration parameters:
|
|
55
|
+
- api_key: Your logdash API key
|
|
56
|
+
- host: logdash API host (defaults to https://api.logdash.io)
|
|
57
|
+
- verbose: Enable verbose mode
|
|
58
|
+
|
|
59
|
+
Returns:
|
|
60
|
+
A logdash instance with logger and metrics properties
|
|
61
|
+
"""
|
|
62
|
+
# Initialize with default values
|
|
63
|
+
api_key = None
|
|
64
|
+
host = "https://api.logdash.io"
|
|
65
|
+
verbose = False
|
|
66
|
+
|
|
67
|
+
# Override with provided params if any
|
|
68
|
+
if params is not None:
|
|
69
|
+
api_key = params.get("api_key", api_key)
|
|
70
|
+
host = params.get("host", host)
|
|
71
|
+
verbose = params.get("verbose", verbose)
|
|
72
|
+
|
|
73
|
+
return logdash(api_key, host, verbose)
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
"""Logger implementation for logdash."""
|
|
2
|
+
|
|
3
|
+
from datetime import datetime
|
|
4
|
+
from typing import Any, Callable, Optional
|
|
5
|
+
|
|
6
|
+
from colorama import Style, init
|
|
7
|
+
|
|
8
|
+
from logdash.constants import LogLevel, LOG_LEVEL_COLORS
|
|
9
|
+
|
|
10
|
+
# Initialize colorama for cross-platform terminal colors
|
|
11
|
+
init()
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
class Logger:
|
|
15
|
+
"""
|
|
16
|
+
A flexible logger for terminal output and remote logging.
|
|
17
|
+
|
|
18
|
+
The Logger provides methods for different log levels and can
|
|
19
|
+
both print locally and send logs to a remote service.
|
|
20
|
+
"""
|
|
21
|
+
|
|
22
|
+
def __init__(
|
|
23
|
+
self,
|
|
24
|
+
log_method: Callable = print,
|
|
25
|
+
prefix: Optional[Callable[[LogLevel], str]] = None,
|
|
26
|
+
on_log: Optional[Callable[[LogLevel, str], None]] = None,
|
|
27
|
+
):
|
|
28
|
+
"""
|
|
29
|
+
Initialize a new Logger instance.
|
|
30
|
+
|
|
31
|
+
Args:
|
|
32
|
+
log_method: Function to use for local logging (default: print)
|
|
33
|
+
prefix: Optional function to generate log level prefix
|
|
34
|
+
on_log: Optional callback for when logs are generated
|
|
35
|
+
"""
|
|
36
|
+
self.log_method = log_method
|
|
37
|
+
self.prefix = prefix or (lambda level: f"{level.value.upper()} ")
|
|
38
|
+
self.on_log = on_log
|
|
39
|
+
|
|
40
|
+
def error(self, *data: Any) -> None:
|
|
41
|
+
"""Log an error message."""
|
|
42
|
+
self._log(LogLevel.ERROR, " ".join(str(item) for item in data))
|
|
43
|
+
|
|
44
|
+
def warn(self, *data: Any) -> None:
|
|
45
|
+
"""Log a warning message."""
|
|
46
|
+
self._log(LogLevel.WARN, " ".join(str(item) for item in data))
|
|
47
|
+
|
|
48
|
+
def info(self, *data: Any) -> None:
|
|
49
|
+
"""Log an info message."""
|
|
50
|
+
self._log(LogLevel.INFO, " ".join(str(item) for item in data))
|
|
51
|
+
|
|
52
|
+
def log(self, *data: Any) -> None:
|
|
53
|
+
"""Alias for info()."""
|
|
54
|
+
self.info(*data)
|
|
55
|
+
|
|
56
|
+
def http(self, *data: Any) -> None:
|
|
57
|
+
"""Log an HTTP-related message."""
|
|
58
|
+
self._log(LogLevel.HTTP, " ".join(str(item) for item in data))
|
|
59
|
+
|
|
60
|
+
def verbose(self, *data: Any) -> None:
|
|
61
|
+
"""Log a verbose message."""
|
|
62
|
+
self._log(LogLevel.VERBOSE, " ".join(str(item) for item in data))
|
|
63
|
+
|
|
64
|
+
def debug(self, *data: Any) -> None:
|
|
65
|
+
"""Log a debug message."""
|
|
66
|
+
self._log(LogLevel.DEBUG, " ".join(str(item) for item in data))
|
|
67
|
+
|
|
68
|
+
def silly(self, *data: Any) -> None:
|
|
69
|
+
"""Log a silly message (lowest priority)."""
|
|
70
|
+
self._log(LogLevel.SILLY, " ".join(str(item) for item in data))
|
|
71
|
+
|
|
72
|
+
def _log(self, level: LogLevel, message: str) -> None:
|
|
73
|
+
"""
|
|
74
|
+
Internal method to format and output a log message.
|
|
75
|
+
|
|
76
|
+
Args:
|
|
77
|
+
level: The log level
|
|
78
|
+
message: The message to log
|
|
79
|
+
"""
|
|
80
|
+
# Format with color
|
|
81
|
+
color = LOG_LEVEL_COLORS[level]
|
|
82
|
+
timestamp = datetime.now().isoformat()
|
|
83
|
+
|
|
84
|
+
# Format the message with timestamp and level prefix
|
|
85
|
+
formatted_message = (
|
|
86
|
+
f"\033[90m[{timestamp}]\033[0m "
|
|
87
|
+
f"{color}{self.prefix(level)}\033[0m"
|
|
88
|
+
f"{message}"
|
|
89
|
+
)
|
|
90
|
+
|
|
91
|
+
# Output to configured log method
|
|
92
|
+
self.log_method(formatted_message)
|
|
93
|
+
|
|
94
|
+
# Call the callback if configured
|
|
95
|
+
if self.on_log:
|
|
96
|
+
self.on_log(level, message)
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
"""Metrics tracking package for logdash."""
|
|
2
|
+
|
|
3
|
+
from logdash.metrics.base import BaseMetrics
|
|
4
|
+
from logdash.metrics.impl import Metrics
|
|
5
|
+
from logdash.metrics.noop import NoopMetrics
|
|
6
|
+
from logdash.constants import MetricOperation
|
|
7
|
+
|
|
8
|
+
__all__ = ["BaseMetrics", "Metrics", "NoopMetrics", "MetricOperation"]
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
"""Base class for metrics implementations."""
|
|
2
|
+
|
|
3
|
+
from abc import ABC, abstractmethod
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
class BaseMetrics(ABC):
|
|
7
|
+
"""Abstract base class for metrics implementations."""
|
|
8
|
+
|
|
9
|
+
@abstractmethod
|
|
10
|
+
def set(self, name: str, value: float) -> None:
|
|
11
|
+
"""
|
|
12
|
+
Set a metric to an absolute value.
|
|
13
|
+
|
|
14
|
+
Args:
|
|
15
|
+
name: The metric name
|
|
16
|
+
value: The value to set
|
|
17
|
+
"""
|
|
18
|
+
pass
|
|
19
|
+
|
|
20
|
+
@abstractmethod
|
|
21
|
+
def mutate(self, name: str, value: float) -> None:
|
|
22
|
+
"""
|
|
23
|
+
Change a metric by a relative value.
|
|
24
|
+
|
|
25
|
+
Args:
|
|
26
|
+
name: The metric name
|
|
27
|
+
value: The amount to change by
|
|
28
|
+
"""
|
|
29
|
+
pass
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
"""Factory function for creating metrics instances."""
|
|
2
|
+
|
|
3
|
+
from logdash.metrics.base import BaseMetrics
|
|
4
|
+
from logdash.metrics.impl import Metrics
|
|
5
|
+
from logdash.metrics.noop import NoopMetrics
|
|
6
|
+
from logdash.internal import internal_logger
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
def create_metrics(api_key: str, host: str, verbose: bool = False) -> BaseMetrics:
|
|
10
|
+
"""
|
|
11
|
+
Create a metrics instance based on the provided parameters.
|
|
12
|
+
|
|
13
|
+
Args:
|
|
14
|
+
api_key: logdash API key
|
|
15
|
+
host: logdash API host
|
|
16
|
+
verbose: Enable verbose mode
|
|
17
|
+
|
|
18
|
+
Returns:
|
|
19
|
+
A BaseMetrics instance
|
|
20
|
+
"""
|
|
21
|
+
if not api_key:
|
|
22
|
+
if verbose:
|
|
23
|
+
internal_logger.warn("No API key provided, using NoopMetrics")
|
|
24
|
+
return NoopMetrics()
|
|
25
|
+
|
|
26
|
+
if verbose:
|
|
27
|
+
internal_logger.verbose(f"Creating Metrics with host {host}")
|
|
28
|
+
|
|
29
|
+
return Metrics(api_key, host, verbose)
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
"""HTTP-based metrics implementation."""
|
|
2
|
+
|
|
3
|
+
import requests
|
|
4
|
+
|
|
5
|
+
from logdash.metrics.base import BaseMetrics
|
|
6
|
+
from logdash.constants import MetricOperation
|
|
7
|
+
from logdash.internal import internal_logger
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class Metrics(BaseMetrics):
|
|
11
|
+
"""
|
|
12
|
+
HTTP-based metrics implementation.
|
|
13
|
+
|
|
14
|
+
Sends metrics to the logdash API via HTTP.
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
def __init__(self, api_key: str, host: str, verbose: bool = False):
|
|
18
|
+
"""
|
|
19
|
+
Initialize a metrics instance.
|
|
20
|
+
|
|
21
|
+
Args:
|
|
22
|
+
api_key: logdash API key
|
|
23
|
+
host: logdash API host
|
|
24
|
+
verbose: Enable verbose mode
|
|
25
|
+
"""
|
|
26
|
+
self.api_key = api_key
|
|
27
|
+
self.host = host
|
|
28
|
+
self.verbose = verbose
|
|
29
|
+
|
|
30
|
+
def set(self, name: str, value: float) -> None:
|
|
31
|
+
"""
|
|
32
|
+
Set a metric to an absolute value.
|
|
33
|
+
|
|
34
|
+
Args:
|
|
35
|
+
name: The metric name
|
|
36
|
+
value: The value to set
|
|
37
|
+
"""
|
|
38
|
+
if self.verbose:
|
|
39
|
+
internal_logger.verbose(f"Setting metric {name} to {value}")
|
|
40
|
+
|
|
41
|
+
self._send_metric(name, value, MetricOperation.SET)
|
|
42
|
+
|
|
43
|
+
def mutate(self, name: str, value: float) -> None:
|
|
44
|
+
"""
|
|
45
|
+
Change a metric by a relative value.
|
|
46
|
+
|
|
47
|
+
Args:
|
|
48
|
+
name: The metric name
|
|
49
|
+
value: The amount to change by
|
|
50
|
+
"""
|
|
51
|
+
if self.verbose:
|
|
52
|
+
internal_logger.verbose(f"Mutating metric {name} by {value}")
|
|
53
|
+
|
|
54
|
+
self._send_metric(name, value, MetricOperation.CHANGE)
|
|
55
|
+
|
|
56
|
+
def _send_metric(self, name: str, value: float, operation: MetricOperation) -> None:
|
|
57
|
+
"""
|
|
58
|
+
Send a metric to the logdash API.
|
|
59
|
+
|
|
60
|
+
Args:
|
|
61
|
+
name: The metric name
|
|
62
|
+
value: The metric value
|
|
63
|
+
operation: The operation to perform
|
|
64
|
+
"""
|
|
65
|
+
# Skip if no API key is provided
|
|
66
|
+
if not self.api_key:
|
|
67
|
+
return
|
|
68
|
+
|
|
69
|
+
try:
|
|
70
|
+
requests.put(
|
|
71
|
+
f"{self.host}/metrics",
|
|
72
|
+
headers={
|
|
73
|
+
"Content-Type": "application/json",
|
|
74
|
+
"project-api-key": self.api_key,
|
|
75
|
+
},
|
|
76
|
+
json={
|
|
77
|
+
"name": name,
|
|
78
|
+
"value": value,
|
|
79
|
+
"operation": operation,
|
|
80
|
+
},
|
|
81
|
+
timeout=5, # Add timeout to prevent blocking
|
|
82
|
+
)
|
|
83
|
+
except requests.RequestException:
|
|
84
|
+
# Silently fail for now - future: add retry queue
|
|
85
|
+
pass
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
"""No-operation metrics implementation."""
|
|
2
|
+
|
|
3
|
+
from logdash.metrics.base import BaseMetrics
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
class NoopMetrics(BaseMetrics):
|
|
7
|
+
"""
|
|
8
|
+
No-operation metrics implementation.
|
|
9
|
+
|
|
10
|
+
This implementation does nothing when metrics are set or mutated.
|
|
11
|
+
Useful for testing or when no remote metrics collection is needed.
|
|
12
|
+
"""
|
|
13
|
+
|
|
14
|
+
def set(self, name: str, value: float) -> None:
|
|
15
|
+
"""
|
|
16
|
+
Do nothing with the metric.
|
|
17
|
+
|
|
18
|
+
Args:
|
|
19
|
+
name: The metric name
|
|
20
|
+
value: The value to set
|
|
21
|
+
"""
|
|
22
|
+
pass
|
|
23
|
+
|
|
24
|
+
def mutate(self, name: str, value: float) -> None:
|
|
25
|
+
"""
|
|
26
|
+
Do nothing with the metric.
|
|
27
|
+
|
|
28
|
+
Args:
|
|
29
|
+
name: The metric name
|
|
30
|
+
value: The amount to change by
|
|
31
|
+
"""
|
|
32
|
+
pass
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
"""Base class for log synchronization implementations."""
|
|
2
|
+
|
|
3
|
+
from abc import ABC, abstractmethod
|
|
4
|
+
|
|
5
|
+
from logdash.constants import LogLevel
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class LogSync(ABC):
|
|
9
|
+
"""Abstract base class for log synchronization implementations."""
|
|
10
|
+
|
|
11
|
+
@abstractmethod
|
|
12
|
+
def send(self, message: str, level: LogLevel, created_at: str) -> None:
|
|
13
|
+
"""
|
|
14
|
+
Send a log message to the remote service.
|
|
15
|
+
|
|
16
|
+
Args:
|
|
17
|
+
message: The log message content
|
|
18
|
+
level: The log level
|
|
19
|
+
created_at: ISO-formatted timestamp when the log was created
|
|
20
|
+
"""
|
|
21
|
+
pass
|