ominfra 0.0.0.dev192__py3-none-any.whl → 0.0.0.dev194__py3-none-any.whl
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.
- ominfra/clouds/aws/journald2aws/main.py +5 -2
- ominfra/manage/deploy/conf/manager.py +4 -4
- ominfra/manage/deploy/conf/specs.py +2 -2
- ominfra/manage/main.py +3 -3
- ominfra/scripts/journald2aws.py +448 -122
- ominfra/scripts/manage.py +2019 -1700
- ominfra/scripts/supervisor.py +2113 -1742
- ominfra/supervisor/configs.py +4 -3
- ominfra/supervisor/main.py +2 -2
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/METADATA +4 -4
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/RECORD +15 -16
- ominfra/configs.py +0 -129
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/LICENSE +0 -0
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/WHEEL +0 -0
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/entry_points.txt +0 -0
- {ominfra-0.0.0.dev192.dist-info → ominfra-0.0.0.dev194.dist-info}/top_level.txt +0 -0
ominfra/scripts/journald2aws.py
CHANGED
@@ -9,6 +9,7 @@ import argparse
|
|
9
9
|
import base64
|
10
10
|
import collections
|
11
11
|
import collections.abc
|
12
|
+
import configparser
|
12
13
|
import contextlib
|
13
14
|
import dataclasses as dc
|
14
15
|
import datetime
|
@@ -52,7 +53,13 @@ if sys.version_info < (3, 8):
|
|
52
53
|
########################################
|
53
54
|
|
54
55
|
|
55
|
-
# ../../../../
|
56
|
+
# ../../../../omlish/configs/types.py
|
57
|
+
ConfigMap = ta.Mapping[str, ta.Any]
|
58
|
+
|
59
|
+
# ../../../../omlish/formats/ini/sections.py
|
60
|
+
IniSectionSettingsMap = ta.Mapping[str, ta.Mapping[str, ta.Union[str, ta.Sequence[str]]]] # ta.TypeAlias
|
61
|
+
|
62
|
+
# ../../../../omlish/formats/toml/parser.py
|
56
63
|
TomlParseFloat = ta.Callable[[str], ta.Any]
|
57
64
|
TomlKey = ta.Tuple[str, ...]
|
58
65
|
TomlPos = int # ta.TypeAlias
|
@@ -69,13 +76,12 @@ CheckOnRaiseFn = ta.Callable[[Exception], None] # ta.TypeAlias
|
|
69
76
|
CheckExceptionFactory = ta.Callable[..., Exception] # ta.TypeAlias
|
70
77
|
CheckArgsRenderer = ta.Callable[..., ta.Optional[str]] # ta.TypeAlias
|
71
78
|
|
79
|
+
# ../../../../omlish/configs/formats.py
|
80
|
+
ConfigDataT = ta.TypeVar('ConfigDataT', bound='ConfigData')
|
81
|
+
|
72
82
|
# ../../../../omlish/lite/contextmanagers.py
|
73
83
|
ExitStackedT = ta.TypeVar('ExitStackedT', bound='ExitStacked')
|
74
84
|
|
75
|
-
# ../../../configs.py
|
76
|
-
ConfigMapping = ta.Mapping[str, ta.Any]
|
77
|
-
IniConfigSectionSettingsMap = ta.Mapping[str, ta.Mapping[str, ta.Union[str, ta.Sequence[str]]]] # ta.TypeAlias
|
78
|
-
|
79
85
|
# ../../../threadworkers.py
|
80
86
|
ThreadWorkerT = ta.TypeVar('ThreadWorkerT', bound='ThreadWorker')
|
81
87
|
|
@@ -84,7 +90,55 @@ SubprocessChannelOption = ta.Literal['pipe', 'stdout', 'devnull'] # ta.TypeAlia
|
|
84
90
|
|
85
91
|
|
86
92
|
########################################
|
87
|
-
# ../../../../../
|
93
|
+
# ../../../../../omlish/configs/types.py
|
94
|
+
|
95
|
+
|
96
|
+
#
|
97
|
+
|
98
|
+
|
99
|
+
########################################
|
100
|
+
# ../../../../../omlish/formats/ini/sections.py
|
101
|
+
|
102
|
+
|
103
|
+
##
|
104
|
+
|
105
|
+
|
106
|
+
def extract_ini_sections(cp: configparser.ConfigParser) -> IniSectionSettingsMap:
|
107
|
+
config_dct: ta.Dict[str, ta.Any] = {}
|
108
|
+
for sec in cp.sections():
|
109
|
+
cd = config_dct
|
110
|
+
for k in sec.split('.'):
|
111
|
+
cd = cd.setdefault(k, {})
|
112
|
+
cd.update(cp.items(sec))
|
113
|
+
return config_dct
|
114
|
+
|
115
|
+
|
116
|
+
##
|
117
|
+
|
118
|
+
|
119
|
+
def render_ini_sections(
|
120
|
+
settings_by_section: IniSectionSettingsMap,
|
121
|
+
) -> str:
|
122
|
+
out = io.StringIO()
|
123
|
+
|
124
|
+
for i, (section, settings) in enumerate(settings_by_section.items()):
|
125
|
+
if i:
|
126
|
+
out.write('\n')
|
127
|
+
|
128
|
+
out.write(f'[{section}]\n')
|
129
|
+
|
130
|
+
for k, v in settings.items():
|
131
|
+
if isinstance(v, str):
|
132
|
+
out.write(f'{k}={v}\n')
|
133
|
+
else:
|
134
|
+
for vv in v:
|
135
|
+
out.write(f'{k}={vv}\n')
|
136
|
+
|
137
|
+
return out.getvalue()
|
138
|
+
|
139
|
+
|
140
|
+
########################################
|
141
|
+
# ../../../../../omlish/formats/toml/parser.py
|
88
142
|
# SPDX-License-Identifier: MIT
|
89
143
|
# SPDX-FileCopyrightText: 2021 Taneli Hukkinen
|
90
144
|
# Licensed to PSF under a Contributor Agreement.
|
@@ -901,6 +955,129 @@ def toml_make_safe_parse_float(parse_float: TomlParseFloat) -> TomlParseFloat:
|
|
901
955
|
return safe_parse_float
|
902
956
|
|
903
957
|
|
958
|
+
########################################
|
959
|
+
# ../../../../../omlish/formats/toml/writer.py
|
960
|
+
|
961
|
+
|
962
|
+
class TomlWriter:
|
963
|
+
@dc.dataclass(frozen=True)
|
964
|
+
class Literal:
|
965
|
+
s: str
|
966
|
+
|
967
|
+
def __init__(self, out: ta.TextIO) -> None:
|
968
|
+
super().__init__()
|
969
|
+
self._out = out
|
970
|
+
|
971
|
+
self._indent = 0
|
972
|
+
self._wrote_indent = False
|
973
|
+
|
974
|
+
#
|
975
|
+
|
976
|
+
def _w(self, s: str) -> None:
|
977
|
+
if not self._wrote_indent:
|
978
|
+
self._out.write(' ' * self._indent)
|
979
|
+
self._wrote_indent = True
|
980
|
+
self._out.write(s)
|
981
|
+
|
982
|
+
def _nl(self) -> None:
|
983
|
+
self._out.write('\n')
|
984
|
+
self._wrote_indent = False
|
985
|
+
|
986
|
+
def _needs_quote(self, s: str) -> bool:
|
987
|
+
return (
|
988
|
+
not s or
|
989
|
+
any(c in s for c in '\'"\n') or
|
990
|
+
s[0] not in string.ascii_letters
|
991
|
+
)
|
992
|
+
|
993
|
+
def _maybe_quote(self, s: str) -> str:
|
994
|
+
if self._needs_quote(s):
|
995
|
+
return repr(s)
|
996
|
+
else:
|
997
|
+
return s
|
998
|
+
|
999
|
+
#
|
1000
|
+
|
1001
|
+
def write_root(self, obj: ta.Mapping) -> None:
|
1002
|
+
for i, (k, v) in enumerate(obj.items()):
|
1003
|
+
if i:
|
1004
|
+
self._nl()
|
1005
|
+
self._w('[')
|
1006
|
+
self._w(self._maybe_quote(k))
|
1007
|
+
self._w(']')
|
1008
|
+
self._nl()
|
1009
|
+
self.write_table_contents(v)
|
1010
|
+
|
1011
|
+
def write_table_contents(self, obj: ta.Mapping) -> None:
|
1012
|
+
for k, v in obj.items():
|
1013
|
+
self.write_key(k)
|
1014
|
+
self._w(' = ')
|
1015
|
+
self.write_value(v)
|
1016
|
+
self._nl()
|
1017
|
+
|
1018
|
+
def write_array(self, obj: ta.Sequence) -> None:
|
1019
|
+
self._w('[')
|
1020
|
+
self._nl()
|
1021
|
+
self._indent += 1
|
1022
|
+
for e in obj:
|
1023
|
+
self.write_value(e)
|
1024
|
+
self._w(',')
|
1025
|
+
self._nl()
|
1026
|
+
self._indent -= 1
|
1027
|
+
self._w(']')
|
1028
|
+
|
1029
|
+
def write_inline_table(self, obj: ta.Mapping) -> None:
|
1030
|
+
self._w('{')
|
1031
|
+
for i, (k, v) in enumerate(obj.items()):
|
1032
|
+
if i:
|
1033
|
+
self._w(', ')
|
1034
|
+
self.write_key(k)
|
1035
|
+
self._w(' = ')
|
1036
|
+
self.write_value(v)
|
1037
|
+
self._w('}')
|
1038
|
+
|
1039
|
+
def write_inline_array(self, obj: ta.Sequence) -> None:
|
1040
|
+
self._w('[')
|
1041
|
+
for i, e in enumerate(obj):
|
1042
|
+
if i:
|
1043
|
+
self._w(', ')
|
1044
|
+
self.write_value(e)
|
1045
|
+
self._w(']')
|
1046
|
+
|
1047
|
+
def write_key(self, obj: ta.Any) -> None:
|
1048
|
+
if isinstance(obj, TomlWriter.Literal):
|
1049
|
+
self._w(obj.s)
|
1050
|
+
elif isinstance(obj, str):
|
1051
|
+
self._w(self._maybe_quote(obj.replace('_', '-')))
|
1052
|
+
elif isinstance(obj, int):
|
1053
|
+
self._w(repr(str(obj)))
|
1054
|
+
else:
|
1055
|
+
raise TypeError(obj)
|
1056
|
+
|
1057
|
+
def write_value(self, obj: ta.Any) -> None:
|
1058
|
+
if isinstance(obj, bool):
|
1059
|
+
self._w(str(obj).lower())
|
1060
|
+
elif isinstance(obj, (str, int, float)):
|
1061
|
+
self._w(repr(obj))
|
1062
|
+
elif isinstance(obj, ta.Mapping):
|
1063
|
+
self.write_inline_table(obj)
|
1064
|
+
elif isinstance(obj, ta.Sequence):
|
1065
|
+
if not obj:
|
1066
|
+
self.write_inline_array(obj)
|
1067
|
+
else:
|
1068
|
+
self.write_array(obj)
|
1069
|
+
else:
|
1070
|
+
raise TypeError(obj)
|
1071
|
+
|
1072
|
+
#
|
1073
|
+
|
1074
|
+
@classmethod
|
1075
|
+
def write_str(cls, obj: ta.Any) -> str:
|
1076
|
+
out = io.StringIO()
|
1077
|
+
cls(out).write_value(obj)
|
1078
|
+
return out.getvalue()
|
1079
|
+
|
1080
|
+
|
904
1081
|
########################################
|
905
1082
|
# ../../../../../omlish/lite/cached.py
|
906
1083
|
|
@@ -2218,6 +2395,235 @@ class JournalctlToAwsCursor:
|
|
2218
2395
|
os.rename(ncf, cf)
|
2219
2396
|
|
2220
2397
|
|
2398
|
+
########################################
|
2399
|
+
# ../../../../../omlish/configs/formats.py
|
2400
|
+
"""
|
2401
|
+
Notes:
|
2402
|
+
- necessarily string-oriented
|
2403
|
+
- single file, as this is intended to be amalg'd and thus all included anyway
|
2404
|
+
|
2405
|
+
TODO:
|
2406
|
+
- ConfigDataMapper? to_map -> ConfigMap?
|
2407
|
+
- nginx ?
|
2408
|
+
- raw ?
|
2409
|
+
"""
|
2410
|
+
|
2411
|
+
|
2412
|
+
##
|
2413
|
+
|
2414
|
+
|
2415
|
+
@dc.dataclass(frozen=True)
|
2416
|
+
class ConfigData(abc.ABC): # noqa
|
2417
|
+
@abc.abstractmethod
|
2418
|
+
def as_map(self) -> ConfigMap:
|
2419
|
+
raise NotImplementedError
|
2420
|
+
|
2421
|
+
|
2422
|
+
#
|
2423
|
+
|
2424
|
+
|
2425
|
+
class ConfigLoader(abc.ABC, ta.Generic[ConfigDataT]):
|
2426
|
+
@property
|
2427
|
+
def file_exts(self) -> ta.Sequence[str]:
|
2428
|
+
return ()
|
2429
|
+
|
2430
|
+
def match_file(self, n: str) -> bool:
|
2431
|
+
return '.' in n and n.split('.')[-1] in check.not_isinstance(self.file_exts, str)
|
2432
|
+
|
2433
|
+
#
|
2434
|
+
|
2435
|
+
def load_file(self, p: str) -> ConfigDataT:
|
2436
|
+
with open(p) as f:
|
2437
|
+
return self.load_str(f.read())
|
2438
|
+
|
2439
|
+
@abc.abstractmethod
|
2440
|
+
def load_str(self, s: str) -> ConfigDataT:
|
2441
|
+
raise NotImplementedError
|
2442
|
+
|
2443
|
+
|
2444
|
+
#
|
2445
|
+
|
2446
|
+
|
2447
|
+
class ConfigRenderer(abc.ABC, ta.Generic[ConfigDataT]):
|
2448
|
+
@property
|
2449
|
+
@abc.abstractmethod
|
2450
|
+
def data_cls(self) -> ta.Type[ConfigDataT]:
|
2451
|
+
raise NotImplementedError
|
2452
|
+
|
2453
|
+
def match_data(self, d: ConfigDataT) -> bool:
|
2454
|
+
return isinstance(d, self.data_cls)
|
2455
|
+
|
2456
|
+
#
|
2457
|
+
|
2458
|
+
@abc.abstractmethod
|
2459
|
+
def render(self, d: ConfigDataT) -> str:
|
2460
|
+
raise NotImplementedError
|
2461
|
+
|
2462
|
+
|
2463
|
+
##
|
2464
|
+
|
2465
|
+
|
2466
|
+
@dc.dataclass(frozen=True)
|
2467
|
+
class ObjConfigData(ConfigData, abc.ABC):
|
2468
|
+
obj: ta.Any
|
2469
|
+
|
2470
|
+
def as_map(self) -> ConfigMap:
|
2471
|
+
return check.isinstance(self.obj, collections.abc.Mapping)
|
2472
|
+
|
2473
|
+
|
2474
|
+
##
|
2475
|
+
|
2476
|
+
|
2477
|
+
@dc.dataclass(frozen=True)
|
2478
|
+
class JsonConfigData(ObjConfigData):
|
2479
|
+
pass
|
2480
|
+
|
2481
|
+
|
2482
|
+
class JsonConfigLoader(ConfigLoader[JsonConfigData]):
|
2483
|
+
file_exts = ('json',)
|
2484
|
+
|
2485
|
+
def load_str(self, s: str) -> JsonConfigData:
|
2486
|
+
return JsonConfigData(json.loads(s))
|
2487
|
+
|
2488
|
+
|
2489
|
+
class JsonConfigRenderer(ConfigRenderer[JsonConfigData]):
|
2490
|
+
data_cls = JsonConfigData
|
2491
|
+
|
2492
|
+
def render(self, d: JsonConfigData) -> str:
|
2493
|
+
return json_dumps_pretty(d.obj)
|
2494
|
+
|
2495
|
+
|
2496
|
+
##
|
2497
|
+
|
2498
|
+
|
2499
|
+
@dc.dataclass(frozen=True)
|
2500
|
+
class TomlConfigData(ObjConfigData):
|
2501
|
+
pass
|
2502
|
+
|
2503
|
+
|
2504
|
+
class TomlConfigLoader(ConfigLoader[TomlConfigData]):
|
2505
|
+
file_exts = ('toml',)
|
2506
|
+
|
2507
|
+
def load_str(self, s: str) -> TomlConfigData:
|
2508
|
+
return TomlConfigData(toml_loads(s))
|
2509
|
+
|
2510
|
+
|
2511
|
+
class TomlConfigRenderer(ConfigRenderer[TomlConfigData]):
|
2512
|
+
data_cls = TomlConfigData
|
2513
|
+
|
2514
|
+
def render(self, d: TomlConfigData) -> str:
|
2515
|
+
return TomlWriter.write_str(d.obj)
|
2516
|
+
|
2517
|
+
|
2518
|
+
##
|
2519
|
+
|
2520
|
+
|
2521
|
+
@dc.dataclass(frozen=True)
|
2522
|
+
class YamlConfigData(ObjConfigData):
|
2523
|
+
pass
|
2524
|
+
|
2525
|
+
|
2526
|
+
class YamlConfigLoader(ConfigLoader[YamlConfigData]):
|
2527
|
+
file_exts = ('yaml', 'yml')
|
2528
|
+
|
2529
|
+
def load_str(self, s: str) -> YamlConfigData:
|
2530
|
+
return YamlConfigData(__import__('yaml').safe_load(s))
|
2531
|
+
|
2532
|
+
|
2533
|
+
class YamlConfigRenderer(ConfigRenderer[YamlConfigData]):
|
2534
|
+
data_cls = YamlConfigData
|
2535
|
+
|
2536
|
+
def render(self, d: YamlConfigData) -> str:
|
2537
|
+
return __import__('yaml').safe_dump(d.obj)
|
2538
|
+
|
2539
|
+
|
2540
|
+
##
|
2541
|
+
|
2542
|
+
|
2543
|
+
@dc.dataclass(frozen=True)
|
2544
|
+
class IniConfigData(ConfigData):
|
2545
|
+
sections: IniSectionSettingsMap
|
2546
|
+
|
2547
|
+
def as_map(self) -> ConfigMap:
|
2548
|
+
return self.sections
|
2549
|
+
|
2550
|
+
|
2551
|
+
class IniConfigLoader(ConfigLoader[IniConfigData]):
|
2552
|
+
file_exts = ('ini',)
|
2553
|
+
|
2554
|
+
def load_str(self, s: str) -> IniConfigData:
|
2555
|
+
cp = configparser.ConfigParser()
|
2556
|
+
cp.read_string(s)
|
2557
|
+
return IniConfigData(extract_ini_sections(cp))
|
2558
|
+
|
2559
|
+
|
2560
|
+
class IniConfigRenderer(ConfigRenderer[IniConfigData]):
|
2561
|
+
data_cls = IniConfigData
|
2562
|
+
|
2563
|
+
def render(self, d: IniConfigData) -> str:
|
2564
|
+
return render_ini_sections(d.sections)
|
2565
|
+
|
2566
|
+
|
2567
|
+
##
|
2568
|
+
|
2569
|
+
|
2570
|
+
@dc.dataclass(frozen=True)
|
2571
|
+
class SwitchedConfigFileLoader:
|
2572
|
+
loaders: ta.Sequence[ConfigLoader]
|
2573
|
+
default: ta.Optional[ConfigLoader] = None
|
2574
|
+
|
2575
|
+
def load_file(self, p: str) -> ConfigData:
|
2576
|
+
n = os.path.basename(p)
|
2577
|
+
|
2578
|
+
for l in self.loaders:
|
2579
|
+
if l.match_file(n):
|
2580
|
+
return l.load_file(p)
|
2581
|
+
|
2582
|
+
if (d := self.default) is not None:
|
2583
|
+
return d.load_file(p)
|
2584
|
+
|
2585
|
+
raise NameError(n)
|
2586
|
+
|
2587
|
+
|
2588
|
+
DEFAULT_CONFIG_LOADERS: ta.Sequence[ConfigLoader] = [
|
2589
|
+
JsonConfigLoader(),
|
2590
|
+
TomlConfigLoader(),
|
2591
|
+
YamlConfigLoader(),
|
2592
|
+
IniConfigLoader(),
|
2593
|
+
]
|
2594
|
+
|
2595
|
+
DEFAULT_CONFIG_LOADER: ConfigLoader = JsonConfigLoader()
|
2596
|
+
|
2597
|
+
DEFAULT_CONFIG_FILE_LOADER = SwitchedConfigFileLoader(
|
2598
|
+
loaders=DEFAULT_CONFIG_LOADERS,
|
2599
|
+
default=DEFAULT_CONFIG_LOADER,
|
2600
|
+
)
|
2601
|
+
|
2602
|
+
|
2603
|
+
##
|
2604
|
+
|
2605
|
+
|
2606
|
+
@dc.dataclass(frozen=True)
|
2607
|
+
class SwitchedConfigRenderer:
|
2608
|
+
renderers: ta.Sequence[ConfigRenderer]
|
2609
|
+
|
2610
|
+
def render(self, d: ConfigData) -> str:
|
2611
|
+
for r in self.renderers:
|
2612
|
+
if r.match_data(d):
|
2613
|
+
return r.render(d)
|
2614
|
+
raise TypeError(d)
|
2615
|
+
|
2616
|
+
|
2617
|
+
DEFAULT_CONFIG_RENDERERS: ta.Sequence[ConfigRenderer] = [
|
2618
|
+
JsonConfigRenderer(),
|
2619
|
+
TomlConfigRenderer(),
|
2620
|
+
YamlConfigRenderer(),
|
2621
|
+
IniConfigRenderer(),
|
2622
|
+
]
|
2623
|
+
|
2624
|
+
DEFAULT_CONFIG_RENDERER = SwitchedConfigRenderer(DEFAULT_CONFIG_RENDERERS)
|
2625
|
+
|
2626
|
+
|
2221
2627
|
########################################
|
2222
2628
|
# ../../../../../omlish/io/buffers.py
|
2223
2629
|
|
@@ -3280,121 +3686,6 @@ class AwsLogMessageBuilder:
|
|
3280
3686
|
return [post]
|
3281
3687
|
|
3282
3688
|
|
3283
|
-
########################################
|
3284
|
-
# ../../../../configs.py
|
3285
|
-
|
3286
|
-
|
3287
|
-
##
|
3288
|
-
|
3289
|
-
|
3290
|
-
def parse_config_file(
|
3291
|
-
name: str,
|
3292
|
-
f: ta.TextIO,
|
3293
|
-
) -> ConfigMapping:
|
3294
|
-
if name.endswith('.toml'):
|
3295
|
-
return toml_loads(f.read())
|
3296
|
-
|
3297
|
-
elif any(name.endswith(e) for e in ('.yml', '.yaml')):
|
3298
|
-
yaml = __import__('yaml')
|
3299
|
-
return yaml.safe_load(f)
|
3300
|
-
|
3301
|
-
elif name.endswith('.ini'):
|
3302
|
-
import configparser
|
3303
|
-
cp = configparser.ConfigParser()
|
3304
|
-
cp.read_file(f)
|
3305
|
-
config_dct: ta.Dict[str, ta.Any] = {}
|
3306
|
-
for sec in cp.sections():
|
3307
|
-
cd = config_dct
|
3308
|
-
for k in sec.split('.'):
|
3309
|
-
cd = cd.setdefault(k, {})
|
3310
|
-
cd.update(cp.items(sec))
|
3311
|
-
return config_dct
|
3312
|
-
|
3313
|
-
else:
|
3314
|
-
return json.loads(f.read())
|
3315
|
-
|
3316
|
-
|
3317
|
-
def read_config_file(
|
3318
|
-
path: str,
|
3319
|
-
cls: ta.Type[T],
|
3320
|
-
*,
|
3321
|
-
prepare: ta.Optional[ta.Callable[[ConfigMapping], ConfigMapping]] = None,
|
3322
|
-
msh: ObjMarshalerManager = OBJ_MARSHALER_MANAGER,
|
3323
|
-
) -> T:
|
3324
|
-
with open(path) as cf:
|
3325
|
-
config_dct = parse_config_file(os.path.basename(path), cf)
|
3326
|
-
|
3327
|
-
if prepare is not None:
|
3328
|
-
config_dct = prepare(config_dct)
|
3329
|
-
|
3330
|
-
return msh.unmarshal_obj(config_dct, cls)
|
3331
|
-
|
3332
|
-
|
3333
|
-
##
|
3334
|
-
|
3335
|
-
|
3336
|
-
def build_config_named_children(
|
3337
|
-
o: ta.Union[
|
3338
|
-
ta.Sequence[ConfigMapping],
|
3339
|
-
ta.Mapping[str, ConfigMapping],
|
3340
|
-
None,
|
3341
|
-
],
|
3342
|
-
*,
|
3343
|
-
name_key: str = 'name',
|
3344
|
-
) -> ta.Optional[ta.Sequence[ConfigMapping]]:
|
3345
|
-
if o is None:
|
3346
|
-
return None
|
3347
|
-
|
3348
|
-
lst: ta.List[ConfigMapping] = []
|
3349
|
-
if isinstance(o, ta.Mapping):
|
3350
|
-
for k, v in o.items():
|
3351
|
-
check.isinstance(v, ta.Mapping)
|
3352
|
-
if name_key in v:
|
3353
|
-
n = v[name_key]
|
3354
|
-
if k != n:
|
3355
|
-
raise KeyError(f'Given names do not match: {n} != {k}')
|
3356
|
-
lst.append(v)
|
3357
|
-
else:
|
3358
|
-
lst.append({name_key: k, **v})
|
3359
|
-
|
3360
|
-
else:
|
3361
|
-
check.not_isinstance(o, str)
|
3362
|
-
lst.extend(o)
|
3363
|
-
|
3364
|
-
seen = set()
|
3365
|
-
for d in lst:
|
3366
|
-
n = d['name']
|
3367
|
-
if n in d:
|
3368
|
-
raise KeyError(f'Duplicate name: {n}')
|
3369
|
-
seen.add(n)
|
3370
|
-
|
3371
|
-
return lst
|
3372
|
-
|
3373
|
-
|
3374
|
-
##
|
3375
|
-
|
3376
|
-
|
3377
|
-
def render_ini_config(
|
3378
|
-
settings_by_section: IniConfigSectionSettingsMap,
|
3379
|
-
) -> str:
|
3380
|
-
out = io.StringIO()
|
3381
|
-
|
3382
|
-
for i, (section, settings) in enumerate(settings_by_section.items()):
|
3383
|
-
if i:
|
3384
|
-
out.write('\n')
|
3385
|
-
|
3386
|
-
out.write(f'[{section}]\n')
|
3387
|
-
|
3388
|
-
for k, v in settings.items():
|
3389
|
-
if isinstance(v, str):
|
3390
|
-
out.write(f'{k}={v}\n')
|
3391
|
-
else:
|
3392
|
-
for vv in v:
|
3393
|
-
out.write(f'{k}={vv}\n')
|
3394
|
-
|
3395
|
-
return out.getvalue()
|
3396
|
-
|
3397
|
-
|
3398
3689
|
########################################
|
3399
3690
|
# ../../../../journald/messages.py
|
3400
3691
|
|
@@ -3654,6 +3945,38 @@ class ThreadWorkerGroup:
|
|
3654
3945
|
return dct
|
3655
3946
|
|
3656
3947
|
|
3948
|
+
########################################
|
3949
|
+
# ../../../../../omlish/lite/configs.py
|
3950
|
+
|
3951
|
+
|
3952
|
+
##
|
3953
|
+
|
3954
|
+
|
3955
|
+
def load_config_file_obj(
|
3956
|
+
f: str,
|
3957
|
+
cls: ta.Type[T],
|
3958
|
+
*,
|
3959
|
+
prepare: ta.Union[
|
3960
|
+
ta.Callable[[ConfigMap], ConfigMap],
|
3961
|
+
ta.Iterable[ta.Callable[[ConfigMap], ConfigMap]],
|
3962
|
+
] = (),
|
3963
|
+
msh: ObjMarshalerManager = OBJ_MARSHALER_MANAGER,
|
3964
|
+
) -> T:
|
3965
|
+
config_data = DEFAULT_CONFIG_FILE_LOADER.load_file(f)
|
3966
|
+
|
3967
|
+
config_dct = config_data.as_map()
|
3968
|
+
|
3969
|
+
if prepare is not None:
|
3970
|
+
if isinstance(prepare, ta.Iterable):
|
3971
|
+
pfs = list(prepare)
|
3972
|
+
else:
|
3973
|
+
pfs = [prepare]
|
3974
|
+
for pf in pfs:
|
3975
|
+
config_dct = pf(config_dct)
|
3976
|
+
|
3977
|
+
return msh.unmarshal_obj(config_dct, cls)
|
3978
|
+
|
3979
|
+
|
3657
3980
|
########################################
|
3658
3981
|
# ../../../../../omlish/logs/standard.py
|
3659
3982
|
"""
|
@@ -4934,7 +5257,10 @@ def _main() -> None:
|
|
4934
5257
|
|
4935
5258
|
config: JournalctlToAwsDriver.Config
|
4936
5259
|
if args.config_file:
|
4937
|
-
config =
|
5260
|
+
config = load_config_file_obj(
|
5261
|
+
os.path.expanduser(args.config_file),
|
5262
|
+
JournalctlToAwsDriver.Config,
|
5263
|
+
)
|
4938
5264
|
else:
|
4939
5265
|
config = JournalctlToAwsDriver.Config()
|
4940
5266
|
|