hexlogger 2.0.1__tar.gz → 2.0.3__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.
- {hexlogger-2.0.1 → hexlogger-2.0.3}/PKG-INFO +43 -43
- {hexlogger-2.0.1 → hexlogger-2.0.3}/README.md +42 -42
- hexlogger-2.0.3/hexlogger/__init__.py +25 -0
- hexlogger-2.0.3/hexlogger/_compat.py +9 -0
- hexlogger-2.0.3/hexlogger/colors.py +66 -0
- hexlogger-2.0.3/hexlogger/config.py +107 -0
- hexlogger-2.0.3/hexlogger/core.py +49 -0
- hexlogger-2.0.3/hexlogger/formatting.py +107 -0
- hexlogger-2.0.3/hexlogger/gradient.py +63 -0
- hexlogger-2.0.3/hexlogger/progress.py +146 -0
- hexlogger-2.0.3/hexlogger/styles.py +88 -0
- hexlogger-2.0.3/hexlogger/themes.py +101 -0
- hexlogger-2.0.3/hexlogger/utils.py +74 -0
- hexlogger-2.0.3/hexlogger/widgets.py +140 -0
- {hexlogger-2.0.1 → hexlogger-2.0.3}/hexlogger.egg-info/PKG-INFO +43 -43
- hexlogger-2.0.3/hexlogger.egg-info/SOURCES.txt +19 -0
- {hexlogger-2.0.1 → hexlogger-2.0.3}/pyproject.toml +1 -1
- hexlogger-2.0.1/hexlogger/__init__.py +0 -395
- hexlogger-2.0.1/hexlogger.egg-info/SOURCES.txt +0 -8
- {hexlogger-2.0.1 → hexlogger-2.0.3}/LICENSE +0 -0
- {hexlogger-2.0.1 → hexlogger-2.0.3}/hexlogger.egg-info/dependency_links.txt +0 -0
- {hexlogger-2.0.1 → hexlogger-2.0.3}/hexlogger.egg-info/top_level.txt +0 -0
- {hexlogger-2.0.1 → hexlogger-2.0.3}/setup.cfg +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: hexlogger
|
|
3
|
-
Version: 2.0.
|
|
3
|
+
Version: 2.0.3
|
|
4
4
|
Summary: Premium console logging library with themes, gradients, panels, tables, progress bars, and spinners.
|
|
5
5
|
Author: Itz Montage
|
|
6
6
|
License: MIT
|
|
@@ -85,11 +85,11 @@ hexlogger.fatal("Token invalidated — shutting down")
|
|
|
85
85
|
---
|
|
86
86
|
|
|
87
87
|
|
|
88
|
-
Nine display styles are available. All styles respond to the active theme for color. Switch styles with `hexlogger.
|
|
88
|
+
Nine display styles are available. All styles respond to the active theme for color. Switch styles with `hexlogger.setstyle(name)`.
|
|
89
89
|
|
|
90
90
|
|
|
91
91
|
```python
|
|
92
|
-
hexlogger.
|
|
92
|
+
hexlogger.setstyle("default")
|
|
93
93
|
```
|
|
94
94
|
|
|
95
95
|
```
|
|
@@ -108,7 +108,7 @@ hexlogger.set_style("default")
|
|
|
108
108
|
|
|
109
109
|
|
|
110
110
|
```python
|
|
111
|
-
hexlogger.
|
|
111
|
+
hexlogger.setstyle("box")
|
|
112
112
|
```
|
|
113
113
|
|
|
114
114
|
```
|
|
@@ -127,7 +127,7 @@ hexlogger.set_style("box")
|
|
|
127
127
|
|
|
128
128
|
|
|
129
129
|
```python
|
|
130
|
-
hexlogger.
|
|
130
|
+
hexlogger.setstyle("modern")
|
|
131
131
|
```
|
|
132
132
|
|
|
133
133
|
```
|
|
@@ -146,7 +146,7 @@ hexlogger.set_style("modern")
|
|
|
146
146
|
|
|
147
147
|
|
|
148
148
|
```python
|
|
149
|
-
hexlogger.
|
|
149
|
+
hexlogger.setstyle("bracket")
|
|
150
150
|
```
|
|
151
151
|
|
|
152
152
|
```
|
|
@@ -165,7 +165,7 @@ hexlogger.set_style("bracket")
|
|
|
165
165
|
|
|
166
166
|
|
|
167
167
|
```python
|
|
168
|
-
hexlogger.
|
|
168
|
+
hexlogger.setstyle("arrow")
|
|
169
169
|
```
|
|
170
170
|
|
|
171
171
|
```
|
|
@@ -184,7 +184,7 @@ hexlogger.set_style("arrow")
|
|
|
184
184
|
|
|
185
185
|
|
|
186
186
|
```python
|
|
187
|
-
hexlogger.
|
|
187
|
+
hexlogger.setstyle("pipe")
|
|
188
188
|
```
|
|
189
189
|
|
|
190
190
|
```
|
|
@@ -203,7 +203,7 @@ hexlogger.set_style("pipe")
|
|
|
203
203
|
|
|
204
204
|
|
|
205
205
|
```python
|
|
206
|
-
hexlogger.
|
|
206
|
+
hexlogger.setstyle("tag")
|
|
207
207
|
```
|
|
208
208
|
|
|
209
209
|
```
|
|
@@ -224,7 +224,7 @@ hexlogger.set_style("tag")
|
|
|
224
224
|
|
|
225
225
|
|
|
226
226
|
```python
|
|
227
|
-
hexlogger.
|
|
227
|
+
hexlogger.setstyle("dots")
|
|
228
228
|
```
|
|
229
229
|
|
|
230
230
|
```
|
|
@@ -243,7 +243,7 @@ hexlogger.set_style("dots")
|
|
|
243
243
|
|
|
244
244
|
|
|
245
245
|
```python
|
|
246
|
-
hexlogger.
|
|
246
|
+
hexlogger.setstyle("clean")
|
|
247
247
|
```
|
|
248
248
|
|
|
249
249
|
```
|
|
@@ -266,12 +266,12 @@ hexlogger.set_style("clean")
|
|
|
266
266
|
Six built-in themes control the colors applied to every style. Themes do not affect the structure of the output — only the palette.
|
|
267
267
|
|
|
268
268
|
```python
|
|
269
|
-
hexlogger.
|
|
270
|
-
hexlogger.
|
|
271
|
-
hexlogger.
|
|
272
|
-
hexlogger.
|
|
273
|
-
hexlogger.
|
|
274
|
-
hexlogger.
|
|
269
|
+
hexlogger.settheme("default") # Soft blue/green palette
|
|
270
|
+
hexlogger.settheme("neon") # Vivid cyan/magenta palette
|
|
271
|
+
hexlogger.settheme("minimal") # Muted grays, abbreviated labels
|
|
272
|
+
hexlogger.settheme("hacker") # Green-on-black matrix palette
|
|
273
|
+
hexlogger.settheme("sunset") # Warm orange/red palette
|
|
274
|
+
hexlogger.settheme("ocean") # Deep blue/teal palette
|
|
275
275
|
```
|
|
276
276
|
|
|
277
277
|
The `minimal` theme also uses abbreviated level labels:
|
|
@@ -318,7 +318,7 @@ hexlogger._config.add_theme("mytheme", {
|
|
|
318
318
|
"label_trace": "TRACE",
|
|
319
319
|
})
|
|
320
320
|
|
|
321
|
-
hexlogger.
|
|
321
|
+
hexlogger.settheme("mytheme")
|
|
322
322
|
```
|
|
323
323
|
|
|
324
324
|
---
|
|
@@ -347,13 +347,13 @@ hexlogger.blank(2)
|
|
|
347
347
|
|
|
348
348
|
|
|
349
349
|
```python
|
|
350
|
-
hexlogger.banner("HexLogger\
|
|
350
|
+
hexlogger.banner("HexLogger\nv3.0.0")
|
|
351
351
|
```
|
|
352
352
|
|
|
353
353
|
```
|
|
354
354
|
╔═══════════════╗
|
|
355
355
|
║ HexLogger ║
|
|
356
|
-
║
|
|
356
|
+
║ v3.0.0 ║
|
|
357
357
|
╚═══════════════╝
|
|
358
358
|
```
|
|
359
359
|
|
|
@@ -430,31 +430,31 @@ hexlogger.pair("Users", "94,210")
|
|
|
430
430
|
|
|
431
431
|
|
|
432
432
|
```python
|
|
433
|
-
hexlogger.
|
|
434
|
-
hexlogger.
|
|
433
|
+
hexlogger.gprint("Hello World!", (255, 0, 100), (100, 0, 255))
|
|
434
|
+
hexlogger.rbprint("Rainbow text!")
|
|
435
435
|
|
|
436
|
-
text = hexlogger.
|
|
437
|
-
multi = hexlogger.
|
|
436
|
+
text = hexlogger.gtext("Custom gradient", (0, 255, 200), (255, 0, 100))
|
|
437
|
+
multi = hexlogger.mgtext("Multi-stop", [(255,0,0), (0,255,0), (0,0,255)])
|
|
438
438
|
```
|
|
439
439
|
|
|
440
440
|
|
|
441
441
|
```python
|
|
442
|
-
from hexlogger import bold, italic,
|
|
442
|
+
from hexlogger import bold, italic, uline, clr, Colors
|
|
443
443
|
|
|
444
444
|
print(bold("Bold text"))
|
|
445
445
|
print(italic("Italic text"))
|
|
446
|
-
print(
|
|
447
|
-
print(
|
|
446
|
+
print(uline("Underlined text"))
|
|
447
|
+
print(clr("Cyan text", Colors.CYAN))
|
|
448
448
|
```
|
|
449
449
|
|
|
450
450
|
|
|
451
451
|
```python
|
|
452
|
-
from hexlogger import rgb,
|
|
452
|
+
from hexlogger import rgb, bgrgb, hexclr, bghex
|
|
453
453
|
|
|
454
454
|
color = rgb(255, 128, 0)
|
|
455
|
-
bg =
|
|
456
|
-
from_hex =
|
|
457
|
-
bg_hex_ =
|
|
455
|
+
bg = bgrgb(30, 30, 30)
|
|
456
|
+
from_hex = hexclr("#FF8800")
|
|
457
|
+
bg_hex_ = bghex("#1E1E1E")
|
|
458
458
|
```
|
|
459
459
|
|
|
460
460
|
---
|
|
@@ -463,7 +463,7 @@ bg_hex_ = bg_hex("#1E1E1E")
|
|
|
463
463
|
```python
|
|
464
464
|
import time
|
|
465
465
|
|
|
466
|
-
bar = hexlogger.
|
|
466
|
+
bar = hexlogger.Progress(total=100, label="Downloading", width=40)
|
|
467
467
|
for i in range(100):
|
|
468
468
|
time.sleep(0.05)
|
|
469
469
|
bar.update()
|
|
@@ -521,10 +521,10 @@ elapsed = timer.stop()
|
|
|
521
521
|
|
|
522
522
|
|
|
523
523
|
```python
|
|
524
|
-
hexlogger.
|
|
525
|
-
hexlogger.
|
|
526
|
-
hexlogger.
|
|
527
|
-
hexlogger.
|
|
524
|
+
hexlogger.settheme("neon")
|
|
525
|
+
hexlogger.setstyle("modern")
|
|
526
|
+
hexlogger.setlog("app.log")
|
|
527
|
+
hexlogger.setlevel("warning")
|
|
528
528
|
|
|
529
529
|
hexlogger._config.time_format = "%Y-%m-%d %H:%M:%S"
|
|
530
530
|
hexlogger._config.show_time = False
|
|
@@ -534,13 +534,13 @@ hexlogger._config.show_time = False
|
|
|
534
534
|
Only messages at or above the configured level are printed.
|
|
535
535
|
|
|
536
536
|
```python
|
|
537
|
-
hexlogger.
|
|
538
|
-
hexlogger.
|
|
539
|
-
hexlogger.
|
|
540
|
-
hexlogger.
|
|
541
|
-
hexlogger.
|
|
542
|
-
hexlogger.
|
|
543
|
-
hexlogger.
|
|
537
|
+
hexlogger.setlevel("trace")
|
|
538
|
+
hexlogger.setlevel("debug")
|
|
539
|
+
hexlogger.setlevel("info")
|
|
540
|
+
hexlogger.setlevel("warning")
|
|
541
|
+
hexlogger.setlevel("error")
|
|
542
|
+
hexlogger.setlevel("critical")
|
|
543
|
+
hexlogger.setlevel("fatal")
|
|
544
544
|
```
|
|
545
545
|
|
|
546
546
|
---
|
|
@@ -58,11 +58,11 @@ hexlogger.fatal("Token invalidated — shutting down")
|
|
|
58
58
|
---
|
|
59
59
|
|
|
60
60
|
|
|
61
|
-
Nine display styles are available. All styles respond to the active theme for color. Switch styles with `hexlogger.
|
|
61
|
+
Nine display styles are available. All styles respond to the active theme for color. Switch styles with `hexlogger.setstyle(name)`.
|
|
62
62
|
|
|
63
63
|
|
|
64
64
|
```python
|
|
65
|
-
hexlogger.
|
|
65
|
+
hexlogger.setstyle("default")
|
|
66
66
|
```
|
|
67
67
|
|
|
68
68
|
```
|
|
@@ -81,7 +81,7 @@ hexlogger.set_style("default")
|
|
|
81
81
|
|
|
82
82
|
|
|
83
83
|
```python
|
|
84
|
-
hexlogger.
|
|
84
|
+
hexlogger.setstyle("box")
|
|
85
85
|
```
|
|
86
86
|
|
|
87
87
|
```
|
|
@@ -100,7 +100,7 @@ hexlogger.set_style("box")
|
|
|
100
100
|
|
|
101
101
|
|
|
102
102
|
```python
|
|
103
|
-
hexlogger.
|
|
103
|
+
hexlogger.setstyle("modern")
|
|
104
104
|
```
|
|
105
105
|
|
|
106
106
|
```
|
|
@@ -119,7 +119,7 @@ hexlogger.set_style("modern")
|
|
|
119
119
|
|
|
120
120
|
|
|
121
121
|
```python
|
|
122
|
-
hexlogger.
|
|
122
|
+
hexlogger.setstyle("bracket")
|
|
123
123
|
```
|
|
124
124
|
|
|
125
125
|
```
|
|
@@ -138,7 +138,7 @@ hexlogger.set_style("bracket")
|
|
|
138
138
|
|
|
139
139
|
|
|
140
140
|
```python
|
|
141
|
-
hexlogger.
|
|
141
|
+
hexlogger.setstyle("arrow")
|
|
142
142
|
```
|
|
143
143
|
|
|
144
144
|
```
|
|
@@ -157,7 +157,7 @@ hexlogger.set_style("arrow")
|
|
|
157
157
|
|
|
158
158
|
|
|
159
159
|
```python
|
|
160
|
-
hexlogger.
|
|
160
|
+
hexlogger.setstyle("pipe")
|
|
161
161
|
```
|
|
162
162
|
|
|
163
163
|
```
|
|
@@ -176,7 +176,7 @@ hexlogger.set_style("pipe")
|
|
|
176
176
|
|
|
177
177
|
|
|
178
178
|
```python
|
|
179
|
-
hexlogger.
|
|
179
|
+
hexlogger.setstyle("tag")
|
|
180
180
|
```
|
|
181
181
|
|
|
182
182
|
```
|
|
@@ -197,7 +197,7 @@ hexlogger.set_style("tag")
|
|
|
197
197
|
|
|
198
198
|
|
|
199
199
|
```python
|
|
200
|
-
hexlogger.
|
|
200
|
+
hexlogger.setstyle("dots")
|
|
201
201
|
```
|
|
202
202
|
|
|
203
203
|
```
|
|
@@ -216,7 +216,7 @@ hexlogger.set_style("dots")
|
|
|
216
216
|
|
|
217
217
|
|
|
218
218
|
```python
|
|
219
|
-
hexlogger.
|
|
219
|
+
hexlogger.setstyle("clean")
|
|
220
220
|
```
|
|
221
221
|
|
|
222
222
|
```
|
|
@@ -239,12 +239,12 @@ hexlogger.set_style("clean")
|
|
|
239
239
|
Six built-in themes control the colors applied to every style. Themes do not affect the structure of the output — only the palette.
|
|
240
240
|
|
|
241
241
|
```python
|
|
242
|
-
hexlogger.
|
|
243
|
-
hexlogger.
|
|
244
|
-
hexlogger.
|
|
245
|
-
hexlogger.
|
|
246
|
-
hexlogger.
|
|
247
|
-
hexlogger.
|
|
242
|
+
hexlogger.settheme("default") # Soft blue/green palette
|
|
243
|
+
hexlogger.settheme("neon") # Vivid cyan/magenta palette
|
|
244
|
+
hexlogger.settheme("minimal") # Muted grays, abbreviated labels
|
|
245
|
+
hexlogger.settheme("hacker") # Green-on-black matrix palette
|
|
246
|
+
hexlogger.settheme("sunset") # Warm orange/red palette
|
|
247
|
+
hexlogger.settheme("ocean") # Deep blue/teal palette
|
|
248
248
|
```
|
|
249
249
|
|
|
250
250
|
The `minimal` theme also uses abbreviated level labels:
|
|
@@ -291,7 +291,7 @@ hexlogger._config.add_theme("mytheme", {
|
|
|
291
291
|
"label_trace": "TRACE",
|
|
292
292
|
})
|
|
293
293
|
|
|
294
|
-
hexlogger.
|
|
294
|
+
hexlogger.settheme("mytheme")
|
|
295
295
|
```
|
|
296
296
|
|
|
297
297
|
---
|
|
@@ -320,13 +320,13 @@ hexlogger.blank(2)
|
|
|
320
320
|
|
|
321
321
|
|
|
322
322
|
```python
|
|
323
|
-
hexlogger.banner("HexLogger\
|
|
323
|
+
hexlogger.banner("HexLogger\nv3.0.0")
|
|
324
324
|
```
|
|
325
325
|
|
|
326
326
|
```
|
|
327
327
|
╔═══════════════╗
|
|
328
328
|
║ HexLogger ║
|
|
329
|
-
║
|
|
329
|
+
║ v3.0.0 ║
|
|
330
330
|
╚═══════════════╝
|
|
331
331
|
```
|
|
332
332
|
|
|
@@ -403,31 +403,31 @@ hexlogger.pair("Users", "94,210")
|
|
|
403
403
|
|
|
404
404
|
|
|
405
405
|
```python
|
|
406
|
-
hexlogger.
|
|
407
|
-
hexlogger.
|
|
406
|
+
hexlogger.gprint("Hello World!", (255, 0, 100), (100, 0, 255))
|
|
407
|
+
hexlogger.rbprint("Rainbow text!")
|
|
408
408
|
|
|
409
|
-
text = hexlogger.
|
|
410
|
-
multi = hexlogger.
|
|
409
|
+
text = hexlogger.gtext("Custom gradient", (0, 255, 200), (255, 0, 100))
|
|
410
|
+
multi = hexlogger.mgtext("Multi-stop", [(255,0,0), (0,255,0), (0,0,255)])
|
|
411
411
|
```
|
|
412
412
|
|
|
413
413
|
|
|
414
414
|
```python
|
|
415
|
-
from hexlogger import bold, italic,
|
|
415
|
+
from hexlogger import bold, italic, uline, clr, Colors
|
|
416
416
|
|
|
417
417
|
print(bold("Bold text"))
|
|
418
418
|
print(italic("Italic text"))
|
|
419
|
-
print(
|
|
420
|
-
print(
|
|
419
|
+
print(uline("Underlined text"))
|
|
420
|
+
print(clr("Cyan text", Colors.CYAN))
|
|
421
421
|
```
|
|
422
422
|
|
|
423
423
|
|
|
424
424
|
```python
|
|
425
|
-
from hexlogger import rgb,
|
|
425
|
+
from hexlogger import rgb, bgrgb, hexclr, bghex
|
|
426
426
|
|
|
427
427
|
color = rgb(255, 128, 0)
|
|
428
|
-
bg =
|
|
429
|
-
from_hex =
|
|
430
|
-
bg_hex_ =
|
|
428
|
+
bg = bgrgb(30, 30, 30)
|
|
429
|
+
from_hex = hexclr("#FF8800")
|
|
430
|
+
bg_hex_ = bghex("#1E1E1E")
|
|
431
431
|
```
|
|
432
432
|
|
|
433
433
|
---
|
|
@@ -436,7 +436,7 @@ bg_hex_ = bg_hex("#1E1E1E")
|
|
|
436
436
|
```python
|
|
437
437
|
import time
|
|
438
438
|
|
|
439
|
-
bar = hexlogger.
|
|
439
|
+
bar = hexlogger.Progress(total=100, label="Downloading", width=40)
|
|
440
440
|
for i in range(100):
|
|
441
441
|
time.sleep(0.05)
|
|
442
442
|
bar.update()
|
|
@@ -494,10 +494,10 @@ elapsed = timer.stop()
|
|
|
494
494
|
|
|
495
495
|
|
|
496
496
|
```python
|
|
497
|
-
hexlogger.
|
|
498
|
-
hexlogger.
|
|
499
|
-
hexlogger.
|
|
500
|
-
hexlogger.
|
|
497
|
+
hexlogger.settheme("neon")
|
|
498
|
+
hexlogger.setstyle("modern")
|
|
499
|
+
hexlogger.setlog("app.log")
|
|
500
|
+
hexlogger.setlevel("warning")
|
|
501
501
|
|
|
502
502
|
hexlogger._config.time_format = "%Y-%m-%d %H:%M:%S"
|
|
503
503
|
hexlogger._config.show_time = False
|
|
@@ -507,13 +507,13 @@ hexlogger._config.show_time = False
|
|
|
507
507
|
Only messages at or above the configured level are printed.
|
|
508
508
|
|
|
509
509
|
```python
|
|
510
|
-
hexlogger.
|
|
511
|
-
hexlogger.
|
|
512
|
-
hexlogger.
|
|
513
|
-
hexlogger.
|
|
514
|
-
hexlogger.
|
|
515
|
-
hexlogger.
|
|
516
|
-
hexlogger.
|
|
510
|
+
hexlogger.setlevel("trace")
|
|
511
|
+
hexlogger.setlevel("debug")
|
|
512
|
+
hexlogger.setlevel("info")
|
|
513
|
+
hexlogger.setlevel("warning")
|
|
514
|
+
hexlogger.setlevel("error")
|
|
515
|
+
hexlogger.setlevel("critical")
|
|
516
|
+
hexlogger.setlevel("fatal")
|
|
517
517
|
```
|
|
518
518
|
|
|
519
519
|
---
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
__version__ = "2.0.3"
|
|
2
|
+
__author__ = "Montage"
|
|
3
|
+
|
|
4
|
+
from .colors import Colors, rgb, bgrgb, hexclr, bghex
|
|
5
|
+
from .themes import Theme, THEMES, LEVEL_ICONS
|
|
6
|
+
from .config import LogLevel, LoggerConfig, settheme, setstyle, setlog, setlevel
|
|
7
|
+
from .core import debug, info, success, warn, warning, error, critical, fatal, trace
|
|
8
|
+
from .formatting import divider, section, blank, rule, banner, pair
|
|
9
|
+
from .gradient import gtext, gprint, mgtext, mgprint, rbtext, rbprint
|
|
10
|
+
from .widgets import panel, table, box
|
|
11
|
+
from .progress import Progress, Spinner, Timer
|
|
12
|
+
from .utils import clr, bold, italic, uline
|
|
13
|
+
from . import _compat
|
|
14
|
+
|
|
15
|
+
__all__ = [
|
|
16
|
+
"debug", "info", "success", "warn", "warning",
|
|
17
|
+
"error", "critical", "fatal", "trace",
|
|
18
|
+
"divider", "section", "blank", "rule", "banner", "pair",
|
|
19
|
+
"gtext", "gprint", "mgtext", "mgprint", "rbtext", "rbprint",
|
|
20
|
+
"panel", "table", "box",
|
|
21
|
+
"Progress", "Spinner", "Timer",
|
|
22
|
+
"clr", "bold", "italic", "uline",
|
|
23
|
+
"Colors", "rgb", "bgrgb", "hexclr", "bghex",
|
|
24
|
+
"Theme", "LogLevel", "settheme", "setstyle", "setlog", "setlevel",
|
|
25
|
+
]
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
__all__ = ["Colors", "rgb", "bgrgb", "hexclr", "bghex"]
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
class Colors:
|
|
5
|
+
RESET = "\033[0m"
|
|
6
|
+
BOLD = "\033[1m"
|
|
7
|
+
DIM = "\033[2m"
|
|
8
|
+
ITALIC = "\033[3m"
|
|
9
|
+
UNDERLINE = "\033[4m"
|
|
10
|
+
BLINK = "\033[5m"
|
|
11
|
+
REVERSE = "\033[7m"
|
|
12
|
+
STRIKE = "\033[9m"
|
|
13
|
+
BLACK = "\033[30m"
|
|
14
|
+
RED = "\033[31m"
|
|
15
|
+
GREEN = "\033[32m"
|
|
16
|
+
YELLOW = "\033[33m"
|
|
17
|
+
BLUE = "\033[34m"
|
|
18
|
+
MAGENTA = "\033[35m"
|
|
19
|
+
CYAN = "\033[36m"
|
|
20
|
+
WHITE = "\033[37m"
|
|
21
|
+
GRAY = "\033[90m"
|
|
22
|
+
BRIGHT_RED = "\033[91m"
|
|
23
|
+
BRIGHT_GREEN = "\033[92m"
|
|
24
|
+
BRIGHT_YELLOW = "\033[93m"
|
|
25
|
+
BRIGHT_BLUE = "\033[94m"
|
|
26
|
+
BRIGHT_MAGENTA = "\033[95m"
|
|
27
|
+
BRIGHT_CYAN = "\033[96m"
|
|
28
|
+
BRIGHT_WHITE = "\033[97m"
|
|
29
|
+
BG_BLACK = "\033[40m"
|
|
30
|
+
BG_RED = "\033[41m"
|
|
31
|
+
BG_GREEN = "\033[42m"
|
|
32
|
+
BG_YELLOW = "\033[43m"
|
|
33
|
+
BG_BLUE = "\033[44m"
|
|
34
|
+
BG_MAGENTA = "\033[45m"
|
|
35
|
+
BG_CYAN = "\033[46m"
|
|
36
|
+
BG_WHITE = "\033[47m"
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
def _clamp(v):
|
|
40
|
+
return max(0, min(255, int(v)))
|
|
41
|
+
|
|
42
|
+
def rgb(r, g, b):
|
|
43
|
+
return f"\033[38;2;{_clamp(r)};{_clamp(g)};{_clamp(b)}m"
|
|
44
|
+
|
|
45
|
+
def bgrgb(r, g, b):
|
|
46
|
+
return f"\033[48;2;{_clamp(r)};{_clamp(g)};{_clamp(b)}m"
|
|
47
|
+
|
|
48
|
+
def hexclr(hex_code):
|
|
49
|
+
try:
|
|
50
|
+
hex_code = str(hex_code).lstrip("#")
|
|
51
|
+
if len(hex_code) < 6:
|
|
52
|
+
hex_code = hex_code.ljust(6, "0")
|
|
53
|
+
r, g, b = int(hex_code[0:2], 16), int(hex_code[2:4], 16), int(hex_code[4:6], 16)
|
|
54
|
+
return rgb(r, g, b)
|
|
55
|
+
except Exception:
|
|
56
|
+
return Colors.RESET
|
|
57
|
+
|
|
58
|
+
def bghex(hex_code):
|
|
59
|
+
try:
|
|
60
|
+
hex_code = str(hex_code).lstrip("#")
|
|
61
|
+
if len(hex_code) < 6:
|
|
62
|
+
hex_code = hex_code.ljust(6, "0")
|
|
63
|
+
r, g, b = int(hex_code[0:2], 16), int(hex_code[2:4], 16), int(hex_code[4:6], 16)
|
|
64
|
+
return bgrgb(r, g, b)
|
|
65
|
+
except Exception:
|
|
66
|
+
return Colors.RESET
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import threading
|
|
2
|
+
from enum import Enum
|
|
3
|
+
|
|
4
|
+
from .themes import Theme, THEMES
|
|
5
|
+
from .styles import STYLES
|
|
6
|
+
|
|
7
|
+
__all__ = ["LogLevel", "LoggerConfig", "get_config", "settheme", "setstyle", "setlog", "setlevel"]
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class LogLevel(Enum):
|
|
11
|
+
TRACE = 0
|
|
12
|
+
DEBUG = 1
|
|
13
|
+
INFO = 2
|
|
14
|
+
SUCCESS = 3
|
|
15
|
+
WARNING = 4
|
|
16
|
+
ERROR = 5
|
|
17
|
+
CRITICAL = 6
|
|
18
|
+
FATAL = 7
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
class LoggerConfig:
|
|
22
|
+
def __init__(self):
|
|
23
|
+
self.theme = THEMES.get("default", Theme("default", {}))
|
|
24
|
+
self.style = "default"
|
|
25
|
+
self.time_format = "%H:%M:%S"
|
|
26
|
+
self.show_time = True
|
|
27
|
+
self.log_file = None
|
|
28
|
+
self.min_level = LogLevel.TRACE
|
|
29
|
+
self._file_handle = None
|
|
30
|
+
self._lock = threading.Lock()
|
|
31
|
+
|
|
32
|
+
def set_theme(self, name):
|
|
33
|
+
if name in THEMES:
|
|
34
|
+
self.theme = THEMES[name]
|
|
35
|
+
else:
|
|
36
|
+
raise ValueError(f"Unknown theme: {name}. Available: {', '.join(THEMES.keys())}")
|
|
37
|
+
|
|
38
|
+
def set_style(self, name):
|
|
39
|
+
if name in STYLES:
|
|
40
|
+
self.style = name
|
|
41
|
+
else:
|
|
42
|
+
raise ValueError(f"Unknown style: {name}. Available: {', '.join(STYLES.keys())}")
|
|
43
|
+
|
|
44
|
+
def add_theme(self, name, colors):
|
|
45
|
+
try:
|
|
46
|
+
theme = Theme(str(name), colors if isinstance(colors, dict) else {})
|
|
47
|
+
THEMES[str(name)] = theme
|
|
48
|
+
return theme
|
|
49
|
+
except Exception:
|
|
50
|
+
raise ValueError(f"Failed to add theme: {name}")
|
|
51
|
+
|
|
52
|
+
def set_log_file(self, path):
|
|
53
|
+
try:
|
|
54
|
+
self.log_file = str(path)
|
|
55
|
+
if self._file_handle:
|
|
56
|
+
try:
|
|
57
|
+
self._file_handle.close()
|
|
58
|
+
except Exception:
|
|
59
|
+
pass
|
|
60
|
+
self._file_handle = open(self.log_file, "a", encoding="utf-8")
|
|
61
|
+
except Exception:
|
|
62
|
+
self._file_handle = None
|
|
63
|
+
raise
|
|
64
|
+
|
|
65
|
+
def close(self):
|
|
66
|
+
if self._file_handle:
|
|
67
|
+
try:
|
|
68
|
+
self._file_handle.close()
|
|
69
|
+
except Exception:
|
|
70
|
+
pass
|
|
71
|
+
self._file_handle = None
|
|
72
|
+
|
|
73
|
+
def __del__(self):
|
|
74
|
+
self.close()
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
_config = LoggerConfig()
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
def get_config():
|
|
81
|
+
return _config
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
def settheme(name):
|
|
85
|
+
_config.set_theme(str(name))
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
def setstyle(name):
|
|
89
|
+
_config.set_style(str(name))
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
def setlog(path):
|
|
93
|
+
_config.set_log_file(str(path))
|
|
94
|
+
|
|
95
|
+
|
|
96
|
+
def setlevel(level):
|
|
97
|
+
mapping = {
|
|
98
|
+
"trace": LogLevel.TRACE, "debug": LogLevel.DEBUG,
|
|
99
|
+
"info": LogLevel.INFO, "success": LogLevel.SUCCESS,
|
|
100
|
+
"warning": LogLevel.WARNING, "error": LogLevel.ERROR,
|
|
101
|
+
"critical": LogLevel.CRITICAL, "fatal": LogLevel.FATAL,
|
|
102
|
+
}
|
|
103
|
+
key = str(level).lower().strip()
|
|
104
|
+
if key in mapping:
|
|
105
|
+
_config.min_level = mapping[key]
|
|
106
|
+
else:
|
|
107
|
+
raise ValueError(f"Unknown level: {level}. Available: {', '.join(mapping.keys())}")
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
from datetime import datetime
|
|
2
|
+
|
|
3
|
+
from .config import get_config, LogLevel
|
|
4
|
+
from .styles import STYLES
|
|
5
|
+
from .utils import strip_ansi
|
|
6
|
+
|
|
7
|
+
__all__ = ["debug", "info", "success", "warn", "warning", "error", "critical", "fatal", "trace"]
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def _get_time():
|
|
11
|
+
try:
|
|
12
|
+
return datetime.now().strftime(get_config().time_format)
|
|
13
|
+
except Exception:
|
|
14
|
+
return ""
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
def _log(level, message, level_enum):
|
|
18
|
+
try:
|
|
19
|
+
cfg = get_config()
|
|
20
|
+
if level_enum.value < cfg.min_level.value:
|
|
21
|
+
return
|
|
22
|
+
t = cfg.theme
|
|
23
|
+
now = _get_time()
|
|
24
|
+
style_fn = STYLES.get(cfg.style, STYLES["default"])
|
|
25
|
+
line = style_fn(now, level, t.get(level), t.get(f"label_{level}"), str(message), t, cfg.show_time)
|
|
26
|
+
with cfg._lock:
|
|
27
|
+
print(line)
|
|
28
|
+
if cfg._file_handle:
|
|
29
|
+
try:
|
|
30
|
+
cfg._file_handle.write(strip_ansi(line) + "\n")
|
|
31
|
+
cfg._file_handle.flush()
|
|
32
|
+
except Exception:
|
|
33
|
+
pass
|
|
34
|
+
except Exception:
|
|
35
|
+
try:
|
|
36
|
+
print(f"[{level.upper()}] {message}")
|
|
37
|
+
except Exception:
|
|
38
|
+
pass
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
def debug(msg): _log("debug", msg, LogLevel.DEBUG)
|
|
42
|
+
def info(msg): _log("info", msg, LogLevel.INFO)
|
|
43
|
+
def success(msg): _log("success", msg, LogLevel.SUCCESS)
|
|
44
|
+
def warn(msg): _log("warning", msg, LogLevel.WARNING)
|
|
45
|
+
def warning(msg): _log("warning", msg, LogLevel.WARNING)
|
|
46
|
+
def error(msg): _log("error", msg, LogLevel.ERROR)
|
|
47
|
+
def critical(msg): _log("critical", msg, LogLevel.CRITICAL)
|
|
48
|
+
def fatal(msg): _log("fatal", msg, LogLevel.FATAL)
|
|
49
|
+
def trace(msg): _log("trace", msg, LogLevel.TRACE)
|