ifstate 1.13.6__py3-none-any.whl → 2.0.0__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.
libifstate/parser/base.py CHANGED
@@ -1,12 +1,26 @@
1
+ from libifstate.hook import HOOK_DIR
1
2
  from libifstate.util import logger
2
3
  from libifstate.exception import ParserValidationError
3
4
  from abc import ABC, abstractmethod
4
5
  from copy import deepcopy
6
+ import os
7
+
8
+
9
+ def get_available_hooks():
10
+ # check if there is a hooks dir before trying to scan it
11
+ if not os.path.isdir(HOOK_DIR):
12
+ return {}
13
+
14
+ hooks = {}
15
+ with os.scandir(HOOK_DIR) as it:
16
+ for dentry in it:
17
+ if dentry.is_file():
18
+ hooks[dentry.name] = {}
19
+ return hooks
5
20
 
6
21
 
7
22
  class Parser(ABC):
8
23
  _default_lo_link = {
9
- 'name': 'lo',
10
24
  'addresses': [
11
25
  '127.0.0.1/8',
12
26
  '::1/128',
@@ -18,79 +32,96 @@ class Parser(ABC):
18
32
  }
19
33
  }
20
34
  _default_ifstates = {
21
- 'ignore': {
22
- 'ipaddr_builtin': [
23
- 'fe80::/10'
24
- ],
25
- 'ipaddr_dynamic': True,
26
- 'ifname_builtin': [
27
- r'^br-[\da-f]{12}',
28
- r'^docker\d+',
29
- r'^ppp\d+$',
30
- r'^veth',
31
- r'^virbr\d+',
32
- r'^vrrp\d*\.\d+$'
33
- ],
34
- 'fdb_builtin': [
35
- r'^33:33:',
36
- r'^01:00:5e:'
37
- ],
38
- 'routes_builtin': [
39
- {'proto': 1},
40
- {'proto': 2},
41
- {'proto': 8},
42
- {'proto': 9},
43
- {'proto': 10},
44
- {'proto': 11},
45
- {'proto': 12},
46
- {'proto': 13},
47
- {'proto': 14},
48
- {'proto': 15},
49
- {'proto': 16},
50
- {'proto': 18},
51
- {'proto': 42},
52
- {'proto': 186},
53
- {'proto': 187},
54
- {'proto': 188},
55
- {'proto': 189},
56
- {'proto': 192},
57
- {'to': 'ff00::/8'},
58
- ],
59
- 'rules_builtin': [
60
- {'proto': 1},
61
- {'proto': 2},
62
- {'proto': 8},
63
- {'proto': 9},
64
- {'proto': 10},
65
- {'proto': 11},
66
- {'proto': 12},
67
- {'proto': 13},
68
- {'proto': 14},
69
- {'proto': 15},
70
- {'proto': 16},
71
- {'proto': 18},
72
- {'proto': 42},
73
- {'proto': 186},
74
- {'proto': 187},
75
- {'proto': 188},
76
- {'proto': 189},
77
- {'proto': 192},
78
- ],
79
- },
80
- 'cshaper': {
81
- 'default': {
82
- 'egress_qdisc': {
83
- 'kind': 'cake',
84
- 'handle': '1:',
85
- },
86
- 'ingress_qdisc': {
87
- 'kind': 'cake',
88
- 'handle': '1:',
89
- },
90
- 'ingress_ifname': {
91
- 'search': r'^\D{1,3}',
92
- 'replace': 'ifb',
35
+ 'parameters': {
36
+ 'cshaper': {
37
+ 'default': {
38
+ 'egress_qdisc': {
39
+ 'kind': 'cake',
40
+ 'handle': '1:',
41
+ },
42
+ 'ingress_qdisc': {
43
+ 'kind': 'cake',
44
+ 'handle': '1:',
45
+ },
46
+ 'ingress_ifname': {
47
+ 'search': r'^\D{1,3}',
48
+ 'replace': 'ifb',
49
+ }
50
+ }
51
+ },
52
+ 'defaults_builtin': [
53
+ {
54
+ 'match': [
55
+ {'ifname': ''}
56
+ ],
57
+ 'clear_addresses': True,
58
+ 'clear_fdb': True,
59
+ 'clear_neighbours': True,
60
+ 'clear_tc': True,
61
+ 'link': {
62
+ 'state': 'down',
63
+ 'master': None
64
+ }
93
65
  }
66
+ ],
67
+ 'ignore': {
68
+ 'ipaddr_builtin': [
69
+ 'fe80::/10'
70
+ ],
71
+ 'ipaddr_dynamic': True,
72
+ 'ifname_builtin': [
73
+ r'^br-[\da-f]{12}',
74
+ r'^docker\d+',
75
+ r'^ppp\d+$',
76
+ r'^veth',
77
+ r'^virbr\d+',
78
+ r'^vrrp\d*\.\d+$'
79
+ ],
80
+ 'fdb_builtin': [
81
+ r'^33:33:',
82
+ r'^01:00:5e:'
83
+ ],
84
+ 'routes_builtin': [
85
+ {'proto': 1},
86
+ {'proto': 2},
87
+ {'proto': 8},
88
+ {'proto': 9},
89
+ {'proto': 10},
90
+ {'proto': 11},
91
+ {'proto': 12},
92
+ {'proto': 13},
93
+ {'proto': 14},
94
+ {'proto': 15},
95
+ {'proto': 16},
96
+ {'proto': 18},
97
+ {'proto': 42},
98
+ {'proto': 186},
99
+ {'proto': 187},
100
+ {'proto': 188},
101
+ {'proto': 189},
102
+ {'proto': 192},
103
+ {'to': 'ff00::/8'},
104
+ ],
105
+ 'rules_builtin': [
106
+ {'proto': 1},
107
+ {'proto': 2},
108
+ {'proto': 8},
109
+ {'proto': 9},
110
+ {'proto': 10},
111
+ {'proto': 11},
112
+ {'proto': 12},
113
+ {'proto': 13},
114
+ {'proto': 14},
115
+ {'proto': 15},
116
+ {'proto': 16},
117
+ {'proto': 18},
118
+ {'proto': 42},
119
+ {'proto': 186},
120
+ {'proto': 187},
121
+ {'proto': 188},
122
+ {'proto': 189},
123
+ {'proto': 192},
124
+ ],
94
125
  }
95
126
  }
96
127
  }
@@ -113,12 +144,12 @@ class Parser(ABC):
113
144
  return a
114
145
 
115
146
  def _update_lo(self, cfg):
116
- if 'interfaces' in cfg:
117
- lo = next((idx for idx, iface in enumerate(cfg['interfaces']) if iface['name'] == 'lo'), None)
118
- if lo is not None:
119
- cfg['interfaces'][lo] = self.merge(deepcopy(Parser._default_lo_link), cfg['interfaces'][lo])
147
+ if 'interfaces' in cfg and isinstance(cfg['interfaces'], dict):
148
+ if 'lo' in cfg['interfaces']:
149
+ cfg['interfaces']['lo'] = self.merge(
150
+ deepcopy(Parser._default_lo_link), cfg['interfaces']['lo'])
120
151
  else:
121
- cfg['interfaces'].append(Parser._default_lo_link)
152
+ cfg['interfaces']['lo'] = Parser._default_lo_link
122
153
 
123
154
  def config(self):
124
155
  # merge builtin defaults with config
@@ -126,7 +157,7 @@ class Parser(ABC):
126
157
 
127
158
  # 'ignore' should still be an object
128
159
  try:
129
- iter(cfg["ignore"])
160
+ iter(cfg["parameters"]["ignore"])
130
161
  except TypeError:
131
162
  raise ParserValidationError("$.ignore: is not of type 'object'")
132
163
 
@@ -135,19 +166,34 @@ class Parser(ABC):
135
166
  for namespace in cfg.get('namespaces', {}):
136
167
  self._update_lo(cfg['namespaces'][namespace])
137
168
 
169
+ # add available hooks
170
+ if "hooks" in cfg["parameters"]:
171
+ hooks = get_available_hooks()
172
+ hooks.update(cfg["parameters"]["hooks"])
173
+ cfg["parameters"]["hooks"] = hooks
174
+ else:
175
+ cfg["parameters"]["hooks"] = get_available_hooks()
176
+
138
177
  # merge builtin defaults
139
- for k in list(cfg["ignore"]):
178
+ if "defaults" in cfg["parameters"]:
179
+ cfg["parameters"]["defaults"].extend(cfg["parameters"]["defaults_builtin"])
180
+ else:
181
+ cfg["parameters"]["defaults"] = cfg["parameters"]["defaults_builtin"]
182
+ del cfg["parameters"]["defaults_builtin"]
183
+
184
+ # merge builtin ignore lists
185
+ for k in list(cfg["parameters"]["ignore"]):
140
186
  if k.endswith("_builtin"):
141
187
  n = k[:-8]
142
- if n in cfg["ignore"]:
188
+ if n in cfg["parameters"]["ignore"]:
143
189
  try:
144
- cfg["ignore"][n] += cfg["ignore"][k]
190
+ cfg["parameters"]["ignore"][n] += cfg["parameters"]["ignore"][k]
145
191
  except TypeError:
146
192
  raise ParserValidationError("$.ignore.{}: is not of type '{}'".format(
147
- n, type(cfg["ignore"][k]).__name__))
193
+ n, type(cfg["parameters"]["ignore"][k]).__name__))
148
194
  else:
149
- cfg["ignore"][n] = cfg["ignore"][k]
150
- del(cfg["ignore"][k])
195
+ cfg["parameters"]["ignore"][n] = cfg["parameters"]["ignore"][k]
196
+ del (cfg["parameters"]["ignore"][k])
151
197
 
152
198
  return cfg
153
199