Add minimal defaults modification based on cnfvar type/mode
[pyi2ncommon] / src / cnfvar / templates.py
1 # The software in this package is distributed under the GNU General
2 # Public License version 2 (with a special exception described below).
3 #
4 # A copy of GNU General Public License (GPL) is included in this distribution,
5 # in the file COPYING.GPL.
6 #
7 # As a special exception, if other files instantiate templates or use macros
8 # or inline functions from this file, or you compile this file and link it
9 # with other works to produce a work based on this file, this file
10 # does not by itself cause the resulting work to be covered
11 # by the GNU General Public License.
12 #
13 # However the source code for this file must still be made available
14 # in accordance with section (3) of the GNU General Public License.
15 #
16 # This exception does not invalidate any other reasons why a work based
17 # on this file might be covered by the GNU General Public License.
18 #
19 # Copyright (c) 2016-2018 Intra2net AG <info@intra2net.com>
20
21 """
22
23 summary
24 ------------------------------------------------------
25 Module for one-step dynamic cnfvar generation from default value templates.
26
27 .. codeauthor:: Intra2net
28
29
30 contents
31 -------------------------------------------------------
32 These templates contain the bare defaults the UI adds upon
33 creation of each major and frequently used cnfvar.
34
35
36 interface
37 ------------------------------------------------------
38
39 """
40
41 import time
42 import logging
43
44 # custom imports
45 from .model import Cnf, CnfList
46
47
48 log = logging.getLogger('pyi2ncommon.cnfvar.templates')
49
50
51 ###############################################################################
52 # MAJOR CNF DEFAULTS
53 ###############################################################################
54
55
56 #: UI defaults for a user instance
57 user_defaults = {
58     "USER_DISABLED": "0",
59     "USER_FULLNAME": "",
60     "USER_GROUPWARE_FOLDER_CALENDAR": "INBOX/Kalender",
61     "USER_GROUPWARE_FOLDER_CONTACTS": "INBOX/Kontakte",
62     "USER_GROUPWARE_FOLDER_DRAFTS": "INBOX/Entwürfe",
63     "USER_GROUPWARE_FOLDER_NOTES": "INBOX/Notizen",
64     "USER_GROUPWARE_FOLDER_OUTBOX": "INBOX/Gesendete Elemente",
65     "USER_GROUPWARE_FOLDER_TASKS": "INBOX/Aufgaben",
66     "USER_GROUPWARE_FOLDER_TRASH": "INBOX/Gelöschte Elemente",
67     # always a member of the 'Alle' group
68     "USER_GROUP_MEMBER_REF": "2",
69     "USER_LOCALE": "",
70     "USER_PASSWORD": "",
71     "USER_TRASH_DELETEDAYS": "30",
72     "USER_WEBMAIL_MESSAGES_PER_PAGE": "25",
73     "USER_WEBMAIL_SIGNATURE": "",
74 }
75 #: UI defaults for a group instance
76 group_defaults = {
77     "GROUP_COMMENT": "",
78     "GROUP_ACCESS_GO_ONLINE_ALLOWED": "1",
79     "GROUP_EMAILFILTER_BAN_FILTERLIST_REF": "-1",
80     "GROUP_EMAIL_RELAY_RIGHTS": "RELAY_FROM_INTRANET",
81     "GROUP_PROXY_PROFILE_REF": "1",
82 }
83 #: UI defaults for an intraclient instance
84 intraclient_defaults = {
85     "INTRACLIENT_COMMENT": "",
86     "INTRACLIENT_DNS_RELAYING_ALLOWED": "1",
87     "INTRACLIENT_EMAIL_RELAYING_ALLOWED": "1",
88     "INTRACLIENT_FIREWALL_RULESET_REF": "5",
89     "INTRACLIENT_IP": "",
90     "INTRACLIENT_MAC": "",
91     "INTRACLIENT_PROXY_PROFILE_REF": "-1",
92 }
93 #: UI defaults for a NIC instance
94 nic_defaults = {
95     "NIC_COMMENT": "",
96     "NIC_DRIVER": "",
97     "NIC_MAC": "",
98     "NIC_TYPE": "UNUSED",
99 }
100 #: UI defaults for a provider instance
101 provider_defaults = {
102     "PROVIDER_PROXY_SERVER": "",
103     "PROVIDER_PROXY_PORT": "",
104     "PROVIDER_PROXY_PASSWORD": "",
105     "PROVIDER_PROXY_LOGIN": "",
106     "PROVIDER_NIC_REF": "1",
107     "PROVIDER_NETMASK": "255.255.0.0",
108     "PROVIDER_MTU_SIZE": "1500",
109     "PROVIDER_MODE": "ROUTER",
110     "PROVIDER_MAILTRANSFER_MODE": "IMMEDIATE",
111     "PROVIDER_LOCALIP": "",
112     "PROVIDER_IP": "",
113     "PROVIDER_FIREWALL_RULESET_REF": "7",
114     "PROVIDER_FALLBACK_TIMEOUT": "60",
115     "PROVIDER_FALLBACK_PROVIDER_REF": "-1",
116     "PROVIDER_EMAIL_RELAY_REF": "-1",
117     "PROVIDER_DYNDNS_WEBCHECKIP": "0",
118     "PROVIDER_DYNDNS_ENABLE": "1",
119     "PROVIDER_DNS_MODE": "ROOT",
120     "PROVIDER_DNS": "",
121     "PROVIDER_BWIDTH_MANAGEMENT_UPSTREAM_SPEED": "",
122     "PROVIDER_BWIDTH_MANAGEMENT_ENABLE": "0",
123     "PROVIDER_BWIDTH_MANAGEMENT_DOWNSTREAM_SPEED": "",
124     "PROVIDER_PINGCHECK_SERVERLIST_REF": "-2",
125 }
126 #: UI defaults for a port forwarding instance
127 port_forwarding_defaults = {
128     "PORT_FORWARDING_DST_IP_REF": "1",
129     "PORT_FORWARDING_DST_PORT": "",
130     "PORT_FORWARDING_DST_PORT_END": "",
131     "PORT_FORWARDING_PROTOCOL_TYPE": "TCP",
132     "PORT_FORWARDING_SRC_PORT": "",
133     "PORT_FORWARDING_SRC_PORT_END": "",
134 }
135 #: UI defaults for a firewall ruleset instance
136 firewall_ruleset_defaults = {
137     "FIREWALL_RULESET_PROFILE_TYPE": "FULL",
138 }
139 #: UI defaults for a proxy accesslist instance
140 proxy_accesslist_defaults = {
141     "PROXY_ACCESSLIST_ENTRY_COUNT": "123",
142     "PROXY_ACCESSLIST_MODE": "1",
143     "PROXY_ACCESSLIST_SIZETYPE": "1",
144     "PROXY_ACCESSLIST_TYPE": "0",
145 }
146 #: UI defaults for a key instance
147 key_own_defaults = {
148     "KEY_OWN_FINGERPRINT_MD5": "",
149     "KEY_OWN_FINGERPRINT_SHA1": "",
150     "KEY_OWN_ID_X509": "CN=net.lan",
151     "KEY_OWN_ISSUER": "CN=, C=, L=, ST=, O=, OU=",
152     "KEY_OWN_KEYSIZE": "2048",
153     "KEY_OWN_HASH_ALGO": "SHA2_256",
154     # TODO: the key own creation is currently too hacky for better sanitized defaults
155     "KEY_OWN_PRIVATE_KEY": "<CREATE_HACK>",
156     # TODO: the key own creation is currently too hacky for better sanitized defaults
157     "KEY_OWN_PUBLIC_KEY": "<CREATE_HACK>",
158     # TODO: the key own creation is currently too hacky for better sanitized defaults
159     "KEY_OWN_REQUEST": "<CREATE_HACK>",
160     "KEY_OWN_SUBJECT": "CN=net.lan",
161     # TODO: the key own creation is currently too hacky for better sanitized defaults
162     "KEY_OWN_VALIDFROM": "00001122T445566",
163     # TODO: the key own creation is currently too hacky for better sanitized defaults
164     "KEY_OWN_VALIDTILL": "99991122T445566",
165     "KEY_OWN_TYPE": "SELF",
166     # the ones bellow should be set when using 'generate' to create the key
167     "KEY_OWN_CREATE_CN": "",
168     "KEY_OWN_CREATE_EMAIL": ""
169 }
170 #: UI defaults for a VPN connection instance
171 vpnconn_defaults = {
172     "VPNCONN_ACTIVATION": "ALWAYS",
173     "VPNCONN_DISABLED": "0",
174     "VPNCONN_DNS_RELAYING_ALLOWED": "1",
175     "VPNCONN_EMAIL_RELAYING_ALLOWED": "1",
176     "VPNCONN_ENCRYPTION_PROFILE_REF": "0",
177     "VPNCONN_FIREWALL_RULESET_REF": "5",
178     "VPNCONN_IKE_VERSION": "1",
179     "VPNCONN_KEY_FOREIGN_REF": "1",
180     "VPNCONN_KEY_OWN_REF": "1",
181     "VPNCONN_KEY_TYPE": "PUBLIC",
182     "VPNCONN_LAN_NAT_IP": "",
183     "VPNCONN_LAN_NAT_MODE": "UNMODIFIED",
184     "VPNCONN_LAN_NAT_NETWORK": "",
185     "VPNCONN_LAN_NIC_REF": "2",
186     "VPNCONN_LAN_NET": "",
187     "VPNCONN_LAN_NETMASK": "255.255.0.0",
188     "VPNCONN_LAN_TYPE": "NIC",
189     "VPNCONN_LIFETIME_IKE": "480",
190     "VPNCONN_LIFETIME_IPSECSA": "60",
191     "VPNCONN_OFFLINE_DETECTION_SEC": "60",
192     "VPNCONN_PEER_DNS": "",
193     "VPNCONN_PEER_IP": "",
194     "VPNCONN_PEER_TYPE": "IP",
195     "VPNCONN_PROXY_PROFILE_REF": "-2",
196     "VPNCONN_PSK": "",
197     "VPNCONN_PSK_FOREIGN_ID": "",
198     "VPNCONN_PSK_FOREIGN_ID_TYPE": "IP",
199     "VPNCONN_PSK_OWN_ID": "",
200     "VPNCONN_PSK_OWN_ID_TYPE": "IP",
201     "VPNCONN_REMOTE_INET_NAT": "1",
202     "VPNCONN_REMOTE_MODECONFIG_IP": "",
203     "VPNCONN_REMOTE_NAT_ENABLE": "0",
204     "VPNCONN_REMOTE_NAT_NETWORK": "",
205     "VPNCONN_REMOTE_NET": "",
206     "VPNCONN_REMOTE_NETMASK": "255.255.0.0",
207     "VPNCONN_REMOTE_TYPE": "CUSTOM",
208     "VPNCONN_RETRIES": "3",
209     "VPNCONN_SECURED": "ESP",
210     "VPNCONN_XAUTH_SERVER_ENABLE": "0"
211 }
212
213
214 ###############################################################################
215 # MINOR CONFIGURATION
216 ###############################################################################
217
218
219 def template(name, value, instance=-1, defaults=None, **kwargs):
220     """
221     Generate a template cnf variable from provided defaults.
222
223     :param str name: cnf variable name
224     :param str value: cnf variable data value
225     :param int instance: cnf variable instance number
226     :param defaults: default child variables to populate the cnf variable with
227     :type defaults: {str, str or {}} or None
228     :returns: generated cnf variable
229     :rtype: :py:class:`Cnf`
230
231     All additional keyword arguments will be used to overwrite the defaults.
232     """
233     log.info(f"Generating a template {name} cnfvar")
234     cnf = Cnf(name, value=value, instance=instance)
235     defaults = {} if defaults is None else defaults
236     cnf.add_children(*[(key, value) for key, value in defaults.items()])
237     for key in kwargs.keys():
238         cnf.children.single_with_name(f"{name}_{key}").value = kwargs[key]
239     return cnf
240
241
242 def user(name, instance=-1, **kwargs):
243     """
244     Generate a user cnf variable.
245
246     :param str name: username for the user
247     :param int instance: instance number for the user
248     :returns: generated cnf variable
249     :rtype: :py:class:`Cnf`
250     """
251     log.info(f"Generating a user {name} cnfvar")
252     user_cnf = template("user", name, instance=instance, defaults=user_defaults, **kwargs)
253     user_cnf.children.single_with_name("user_fullname").value = name.capitalize()
254     return user_cnf
255
256
257 def group(name, instance=-1, **kwargs):
258     """
259     Generate a group cnf variable.
260
261     :param str name: name for the group
262     :param int instance: instance number for the group
263     :returns: generated cnf variable
264     :rtype: :py:class:`Cnf`
265     """
266     log.info(f"Generating a group {name} cnfvar")
267     group_cnf = template("group", name, instance=instance, defaults=group_defaults, **kwargs)
268     return group_cnf
269
270
271 def nic(name, instance=-1, **kwargs):
272     """
273     Generate a nic cnf variable.
274
275     :param str name: tag or comment for the nic describing its use
276     :param int instance: instance number for the nic
277     :returns: generated cnf variable
278     :rtype: :py:class:`Cnf`
279     """
280     log.info(f"Generating a nic cnfvar")
281     nic_cnf = template("nic", "", instance=instance, defaults=nic_defaults, **kwargs)
282     nic_cnf.children.single_with_name("nic_comment").value = name
283     if nic_cnf.children.single_with_name("nic_type").value in ["NATLAN", "PUBLICLAN", "PROXYARP"]:
284         nic_cnf.add_child("nic_lan_ip", "192.168.1.1")
285         nic_cnf.add_child("nic_lan_netmask", "255.255.255.0")
286         nic_cnf.add_child("nic_lan_dns_relaying_allowed", "0")
287         nic_cnf.add_child("nic_lan_email_relaying_allowed", "0")
288         nic_cnf.add_child("nic_lan_nat_into", "0")
289         nic_cnf.add_child("nic_lan_proxy_profile_ref", "-1")
290         nic_cnf.add_child("nic_lan_firewall_ruleset_ref", "1")
291     return nic_cnf
292
293
294 def intraclient(name, instance=-1, **kwargs):
295     """
296     Generate an intraclient cnf variable.
297
298     :param str name: name for the intraclient
299     :param int instance: instance number for the intraclient
300     :returns: generated cnf variable
301     :rtype: :py:class:`Cnf`
302     """
303     log.info(f"Generating an intraclient {name} cnfvar")
304     intraclient_cnf = template("intraclient", name, instance=instance,
305                                defaults=intraclient_defaults, **kwargs)
306     return intraclient_cnf
307
308
309 def provider(name, instance=-1, **kwargs):
310     """
311     Generate a provider cnf variable.
312
313     :param str name: name for the provider
314     :param int instance: instance number for the provider
315     :returns: generated cnf variable
316     :rtype: :py:class:`Cnf`
317     """
318     log.info(f"Generating a provider {name} cnfvar")
319     provider_cnf = template("provider", name, instance=instance,
320                             defaults=provider_defaults, **kwargs)
321     # the validation of the LOCALIP will not be ignored despite choosing a different mode
322     if provider_cnf.children.single_with_name("provider_mode").value not in ["ROUTER", "GWINLAN"]:
323         provider_cnf.children.remove_where(lambda c: c.name == "provider_ip")
324         provider_cnf.children.remove_where(lambda c: c.name == "provider_netmask")
325     if provider_cnf.children.single_with_name("provider_mode").value != "ROUTER":
326         provider_cnf.children.remove_where(lambda c: c.name == "provider_localip")
327     if provider_cnf.children.single_with_name("provider_dns_mode").value != "IP":
328         provider_cnf.children.remove_where(lambda c: c.name == "provider_dns")
329     return provider_cnf
330
331
332 def port_forwarding(name, instance=-1, **kwargs):
333     """
334     Generate a port forwarding cnf variable.
335
336     :param str name: name for the port forwarding mapping
337     :param int instance: instance number for the port forwarding mapping
338     :returns: generated cnf variable
339     :rtype: :py:class:`Cnf`
340     """
341     log.info(f"Generating a port forwarding {name} cnfvar")
342     port_forwarding_cnf = template("port_forwarding", name, instance=instance,
343                                    defaults=port_forwarding_defaults, **kwargs)
344     if port_forwarding_cnf.children.single_with_name("port_forwarding_protocol_type").value == "OTHER":
345         port_forwarding_cnf.children.remove_where(lambda c: c.name == "port_forwarding_src_port")
346         port_forwarding_cnf.children.remove_where(lambda c: c.name == "port_forwarding_dst_port")
347         port_forwarding_cnf.children.remove_where(lambda c: c.name == "port_forwarding_src_port_end")
348         port_forwarding_cnf.children.remove_where(lambda c: c.name == "port_forwarding_dst_port_end")
349         port_forwarding_cnf.add_child("port_forwarding_protocol_num", "47")
350     return port_forwarding_cnf
351
352
353 def firewall_ruleset(name, instance=-1, **kwargs):
354     """
355     Generate a firewall ruleset cnf variable.
356
357     :param str name: name for the firewall ruleset
358     :param int instance: instance number for the firewall ruleset
359     :returns: generated cnf variable
360     :rtype: :py:class:`Cnf`
361     """
362     log.info(f"Generating a firewall ruleset {name} cnfvar")
363     firewall_ruleset_cnf = template("firewall_ruleset", name, instance=instance,
364                                     defaults=firewall_ruleset_defaults, **kwargs)
365     return firewall_ruleset_cnf
366
367
368 def proxy_accesslist(name, instance=-1, **kwargs):
369     """
370     Generate a proxy accesslist cnf variable.
371
372     :param str name: name for the proxy accesslist
373     :param int instance: instance number for the proxy accesslist
374     :returns: generated cnf variable
375     :rtype: :py:class:`Cnf`
376     """
377     log.info(f"Generating a proxy accesslist {name} cnfvar")
378     proxy_accesslist_cnf = template("proxy_accesslist", name, instance=instance,
379                                     defaults=proxy_accesslist_defaults, **kwargs)
380     return proxy_accesslist_cnf
381
382
383 def key_own(name, instance=-1, **kwargs):
384     """
385     Generate an own key cnf variable.
386
387     :param str name: name for the own key
388     :param int instance: instance number for the own key
389     :returns: generated cnf variable
390     :rtype: :py:class:`Cnf`
391     """
392     log.info(f"Generating an own key {name} cnfvar")
393     key_own_cnf = template("key_own", name, instance=instance,
394                            defaults=key_own_defaults, **kwargs)
395     return key_own_cnf
396
397
398 def vpnconn(name, instance=-1, **kwargs):
399     """
400     Generate a vpn connection cnf variable.
401
402     :param str name: name for the vpn connection
403     :param int instance: instance number for the vpn connection
404     :returns: generated cnf variable
405     :rtype: :py:class:`Cnf`
406     """
407     log.info(f"Generating a vpn connection {name} cnfvar")
408     vpnconn_cnf = template("vpnconn", name, instance=instance,
409                            defaults=vpnconn_defaults, **kwargs)
410     if vpnconn_cnf.children.single_with_name("vpnconn_lan_type").value not in ["NIC", "CUSTOM"]:
411         vpnconn_cnf.children.remove_where(lambda c: c.name == "vpnconn_lan_net")
412     if vpnconn_cnf.children.single_with_name("vpnconn_remote_type").value != "CUSTOM":
413         vpnconn_cnf.children.remove_where(lambda c: c.name == "vpnconn_remote_net")
414     if vpnconn_cnf.children.single_with_name("vpnconn_remote_type").value != "MODECONFIG":
415         vpnconn_cnf.children.remove_where(lambda c: c.name == "vpnconn_remote_modeconfig_ip")
416     return vpnconn_cnf