Skip to content

Commit 6a2b348

Browse files
docs: Add guide for using ClpKeyValuePairStreamHandler. (#56)
Co-authored-by: Kirk Rodrigues <[email protected]>
1 parent 0359ef6 commit 6a2b348

File tree

1 file changed

+94
-1
lines changed

1 file changed

+94
-1
lines changed

README.md

Lines changed: 94 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,96 @@ The package is hosted with pypi (https://pypi.org/project/clp-logging/), so it
3030
can be installed with `pip`:
3131

3232
`python3 -m pip install --upgrade clp-logging`
33+
34+
## Logging handlers
3335

34-
## Logger handlers
36+
### ClpKeyValuePairStreamHandler
37+
38+
*New in v0.0.14*
39+
40+
This handler enables applications to write structured log events directly into CLP's key-value pair
41+
(kv-pair) IR stream format. The handler accepts structured log events in the form of Python
42+
dictionaries, where each dictionary entry must abide by the requirements detailed
43+
[below](#key-value-pair-requirements). The handler will also automatically include certain
44+
[metadata](#automatically-generated-kv-pairs) (e.g., the log event's level) with each log event.
45+
46+
> [!NOTE]
47+
> Since this handler accepts structured log events, it doesn't support setting a
48+
> [Formatter][py-logging-formatter] (because the log events don't need to be formatted into a
49+
> string).
50+
51+
> [!WARNING]
52+
> `ClpKeyValuePairStreamHandler` currently doesn't support
53+
> [CLPLogLevelTimeout](#log-level-timeout-feature-clplogleveltimeout). This feature will be added in
54+
> a future release.
55+
56+
#### Key-value pair requirements
57+
58+
`ClpKeyValuePairStreamHandler` requires kv-pairs abide by the following rules:
59+
60+
- Keys must be of type `str`.
61+
- Values must be one of the following types:
62+
- Primitives: `int`, `float`, `str`, `bool`, or `None`.
63+
- Arrays (`list`), where each array:
64+
- may contain primitive values, dictionaries, or nested arrays.
65+
- can be empty.
66+
- Dictionaries (`dict`), where each dictionary:
67+
- must adhere to the aforementioned rules for keys and values.
68+
- can be empty.
69+
70+
#### Automatically generated kv-pairs
71+
72+
In addition to the kv-pairs explicitly logged by the application, the handler will add kv-pairs,
73+
like the log event's level, to each log event. We refer to the former as *user-generated* kv-pairs
74+
and the latter as *auto-generated* kv-pairs.
75+
76+
> [!NOTE]
77+
> The kv-pair IR stream format stores auto-generated kv-pairs separately from user-generated
78+
> kv-pairs, so users don't need to worry about key collisions with the auto-generated keys.
79+
80+
The handler adds the following auto-generated kv-pairs to each log event:
81+
82+
| Key | Value type | Description |
83+
|---------------------|------------|----------------------------------------------------|
84+
| `timestamp` | `dict` | The log event's timestamp |
85+
| - `unix_millisecs` | `int` | The timestamp in milliseconds since the Unix epoch |
86+
| - `utc_offset_secs` | `int` | The timestamp's UTC offset in seconds |
87+
| `level` | `dict` | The log event's level |
88+
| - `name` | `str` | The level's name |
89+
| - `num` | `int` | The level's numeric value |
90+
| `source_location` | `dict` | The source location of the logging statement |
91+
| - `path` | `str` | The source location's path |
92+
| - `line` | `int` | The source location's line number |
93+
94+
### Example: `ClpKeyValuePairStreamHandler`
95+
96+
```python
97+
import logging
98+
from pathlib import Path
99+
from clp_logging.handlers import ClpKeyValuePairStreamHandler
100+
101+
clp_handler = ClpKeyValuePairStreamHandler(open(Path("example.clp.zst"), "wb"))
102+
logger: logging.Logger = logging.getLogger(__name__)
103+
logger.addHandler(clp_handler)
104+
105+
logger.info({
106+
"message": "This is an example message",
107+
"machine_info": {
108+
"uid": 12345,
109+
"ip": "127.0.0.1",
110+
},
111+
})
112+
```
113+
114+
### Reading kv-pair IR streams
115+
116+
The following options are available for reading and deserializing kv-pair IR streams generated by
117+
this handler:
118+
119+
- [clp-ffi-py][clp-ffi-py-pypi]: This library provides a [Deserializer][clp-ffi-py-deserializer-doc]
120+
to access a kv-pair IR stream in Python. [This example][clp-ffi-py-deserializer-example]
121+
illustrates its usage.
122+
- [YScope Log Viewer][2]: This UI can be used to view kv-pair IR streams.
35123

36124
### CLPStreamHandler
37125

@@ -267,3 +355,8 @@ word][7].
267355
[7]: https://docformatter.readthedocs.io/en/latest/faq.html#interaction-with-black
268356
[8]: https://beta.ruff.rs/docs/
269357
[9]: https://github.com/y-scope/clp-ffi-py
358+
359+
[clp-ffi-py-deserializer-doc]: https://github.com/y-scope/clp-ffi-py?tab=readme-ov-file#example-code-using-deserializer-to-read-keyvaluepairlogevents-from-an-ir-stream
360+
[clp-ffi-py-deserializer-example]: https://github.com/y-scope/clp-ffi-py?tab=readme-ov-file#example-code-using-deserializer-to-read-keyvaluepairlogevents-from-an-ir-stream
361+
[clp-ffi-py-pypi]: https://pypi.org/project/clp-ffi-py/
362+
[py-logging-formatter]: https://docs.python.org/3/library/logging.html#logging.Formatter

0 commit comments

Comments
 (0)