blob: a48d95af76953ea9078f0dc9b5e2c456ed15d698 [file] [log] [blame]
Matteo Scandolod2044a42017-08-07 16:08:28 -07001# Copyright 2017-present Open Networking Foundation
2#
3# Licensed under the Apache License, Version 2.0 (the "License");
4# you may not use this file except in compliance with the License.
5# You may obtain a copy of the License at
6#
7# http://www.apache.org/licenses/LICENSE-2.0
8#
9# Unless required by applicable law or agreed to in writing, software
10# distributed under the License is distributed on an "AS IS" BASIS,
11# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12# See the License for the specific language governing permissions and
13# limitations under the License.
14
Zack Williams9a42f872019-02-15 17:56:04 -070015from __future__ import absolute_import
16from .base import xproto_string_type, unquote
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070017
Zack Williams045b63d2019-01-22 16:30:57 -070018
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070019def xproto_type_to_ui_type(f):
20 try:
Zack Williams045b63d2019-01-22 16:30:57 -070021 content_type = f["options"]["content_type"]
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070022 content_type = eval(content_type)
Zack Williams045b63d2019-01-22 16:30:57 -070023 except BaseException:
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070024 content_type = None
25 pass
26
Zack Williams045b63d2019-01-22 16:30:57 -070027 if "choices" in f["options"]:
28 return "select"
29 elif content_type == "date":
30 return "date"
31 elif f["type"] == "bool":
32 return "boolean"
33 elif f["type"] == "string":
34 return xproto_string_type(f["options"])
35 elif f["type"] in ["int", "uint32", "int32"] or "link" in f:
36 return "number"
37 elif f["type"] in ["double", "float"]:
38 return "string"
39
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070040
41def xproto_options_choices_to_dict(choices):
42 list = []
43
44 for c in eval(choices):
Zack Williams045b63d2019-01-22 16:30:57 -070045 list.append({"id": c[0], "label": c[1]})
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070046 if len(list) > 0:
47 return list
48 else:
49 return None
50
Zack Williams045b63d2019-01-22 16:30:57 -070051
Zack Williams9a42f872019-02-15 17:56:04 -070052def xproto_dict_to_sorted_string(d):
53 """
54 sorts the dict by key and returns a string representation, which makes
55 for better consistency when testing
56 """
57 ft = [] # formatted tuples
58 for k, v in sorted(d.items(), key=lambda t: t[0]): # sorted by key
59 if v is not None:
60 ft.append("'%s': '%s'" % (k, v))
61 else:
62 ft.append("'%s': None" % k)
63 return "{%s}" % ", ".join(ft)
64
65
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070066def xproto_validators(f):
67 # To be cleaned up when we formalize validation in xproto
68 validators = []
69
70 # bound-based validators
Zack Williams045b63d2019-01-22 16:30:57 -070071 bound_validators = [("max_length", "maxlength"), ("min", "min"), ("max", "max")]
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070072
73 for v0, v1 in bound_validators:
74 try:
Zack Williams045b63d2019-01-22 16:30:57 -070075 validators.append({"name": v1, "int_value": int(f["options"][v0])})
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070076 except KeyError:
77 pass
78
79 # validators based on content_type
Zack Williams045b63d2019-01-22 16:30:57 -070080 content_type_validators = ["ip", "url", "email"]
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070081
82 for v in content_type_validators:
Zack Williams045b63d2019-01-22 16:30:57 -070083 # if f['name']=='ip': pdb.set_trace()
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070084 try:
Zack Williams045b63d2019-01-22 16:30:57 -070085 val = unquote(f["options"]["content_type"]) == v
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070086 if not val:
87 raise KeyError
88
Zack Williams045b63d2019-01-22 16:30:57 -070089 validators.append({"name": v, "bool_value": True})
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070090 except KeyError:
91 pass
92
93 # required validator
94 try:
Zack Williams045b63d2019-01-22 16:30:57 -070095 required = f["options"]["blank"] == "False" and f["options"]["null"] == "False"
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070096 if required:
Zack Williams045b63d2019-01-22 16:30:57 -070097 validators.append({"name": "required", "bool_value": required})
Matteo Scandolo292cc2a2017-07-31 19:02:12 -070098 except KeyError:
99 pass
100
101 return validators
102
Zack Williams045b63d2019-01-22 16:30:57 -0700103
Matteo Scandolo292cc2a2017-07-31 19:02:12 -0700104def is_number(s):
105 try:
106 float(s)
107 return True
108 except ValueError:
109 return False
110
Zack Williams045b63d2019-01-22 16:30:57 -0700111
Matteo Scandolo292cc2a2017-07-31 19:02:12 -0700112def xproto_default_to_gui(default):
Scott Baker4839dec2019-02-27 16:50:37 -0800113 # TODO: Using `eval` here is potentially dangerous as it may allow code injection
Matteo Scandolo292cc2a2017-07-31 19:02:12 -0700114 val = "null"
Scott Baker4839dec2019-02-27 16:50:37 -0800115 try:
116 if is_number(default):
117 val = str(default)
118 elif eval(default) is True:
119 val = "true"
120 elif eval(default) is False:
121 val = "false"
122 elif eval(default) is None:
123 val = "null"
124 else:
125 val = str(default)
126 except NameError:
127 # val was a function call, and we can't pass those to the GUI
Zack Williams045b63d2019-01-22 16:30:57 -0700128 val = "null"
Scott Baker4839dec2019-02-27 16:50:37 -0800129
Matteo Scandolo1f826a42017-08-02 12:02:02 -0700130 return val
131
132
133def xproto_links_to_modeldef_relations(llst):
134 outlist = []
135 seen = []
136 for l in llst:
137 try:
Zack Williams045b63d2019-01-22 16:30:57 -0700138 t = l["link_type"]
139 except KeyError as e:
Matteo Scandolo1f826a42017-08-02 12:02:02 -0700140 raise e
141
Zack Williams045b63d2019-01-22 16:30:57 -0700142 if l["peer"]["fqn"] not in seen and t != "manytomany":
143 on_field = "null"
144 if l["link_type"] == "manytoone":
145 on_field = l["src_port"]
146 elif l["link_type"] == "onetomany":
147 on_field = l["dst_port"]
148 outlist.append(
Zack Williamsbe5ee1c2019-03-18 15:33:07 -0700149 "{model: %s, type: %s, on_field: %s}"
Zack Williams045b63d2019-01-22 16:30:57 -0700150 % (l["peer"]["name"], l["link_type"], on_field)
151 )
152 seen.append(l["peer"])
Matteo Scandolo1f826a42017-08-02 12:02:02 -0700153
Sapan Bhatiabfb233a2018-02-09 14:53:09 -0800154 return outlist