blob: 76f51b8370d83081bbeae508f06adece9c1e2594 [file] [log] [blame]
elinuxhenrikb033eaf2020-02-03 16:02:21 +01001#!/u:sr/bin/env python3
2import copy
3import datetime
4import json
5import logging
6#import requests
7
8from connexion import NoContent
9from flask import Flask, escape, request, make_response
10from jsonschema import validate
11from random import random, choice
12from var_declaration import policy_instances, policy_types, policy_status, policy_type_per_instance
13
14def get_all_policy_identities():
15 if len(request.args) == 0:
16 return(list(policy_instances.keys()), 200)
17 elif 'policyTypeId' in request.args:
18 policyTypeId = request.args.get('policyTypeId')
19 if policyTypeId not in list(policy_types.keys()):
20 return(set_error(None, "The policy type provided does not exist.", 400, "The policy type " + data["policyTypeId"] + " is not defined as a policy type.", None, None, "policyTypeId", None))
21 else:
22 return(list({key for key in policy_instances.keys() if policy_type_per_instance[key]==policyTypeId}), 200)
23 else:
24 return(send_error_code(request.args))
25
26def put_policy(policyId):
27 data = request.data.decode("utf-8")
28 data = data.replace("'", "\"")
29 data = json.loads(data)
30 ps = {}
31 if 'policyTypeId' in request.args:
32 policyTypeId = request.args.get('policyTypeId')
33
34 if policyTypeId not in list(policy_types.keys()):
35 return(set_error(None, "The policy type provided does not exist.", 400, "The policy type " + policyTypeId + " is not defined as a policy type.", None, None, "policyTypeId", None))
36
37 policy_schema = policy_types[policyTypeId]["policySchema"]
38 try:
39 validate(instance=data, schema=policy_schema)
40 except:
41 return(set_error(None, "The json does not validate against the schema.", 400, None, None, None, None, None))
42
43 for i in list(policy_instances.keys()):
44 if policyId != i and \
45 data == policy_instances[i] and \
46 policyTypeId == policy_type_per_instance[i]:
47 return(set_error(None, "The policy already exists with a different id.", 400, "No action has been taken. The id of the existing policy instance is: " + i + ".", None, None, None, None))
48
49 if policyId in list(policy_instances.keys()):
50 if data["scope"] != policy_instances[policyId]["scope"]:
51 return(set_error(None, "The policy already exists with a different scope.", 400, "The policy put involves a modification of the existing scope, which is not allowed.", None, None, "scope", None))
52
53 if 'code' in request.args:
54 return(send_error_code(request.args))
55
56 policy_instances[policyId] = data
57 policy_status[policyId] = set_status("UNDEFINED")
58 if 'policyTypeId' in request.args:
59 status_schema = policy_types[policyTypeId]["statusSchema"]
60 try:
61 validate(instance=policy_status[policyId], schema=status_schema)
62 except:
63 return(set_error(None, "The json does not validate against the status schema.", 400, None, None, None, None, None))
64 policy_type_per_instance[policyId] = policyTypeId
65 else:
66 policy_type_per_instance[policyId] = "UNDEFINED"
67
68 if policyId in policy_instances.keys():
69 code = 201
70 else:
71 code = 200
72
73 response = make_response(policy_instances[policyId], code)
74 if code == 201:
75 response.headers['Location'] = "http://localhost:8085/A1-P/v1/policies/" + policyId
76 return response
77
78def set_status(*args):
79 ps = {}
80 ps["enforceStatus"] = args[0]
81 if len(args) == 2:
82 ps["enforceReason"] = args[1]
83 if len(args) > 2:
84 return(set_error(None, "Too many arguments", 400, "There should be no more than two status arguments: enforceStatus and enforceReason", None, None, None, None))
85 return ps
86
87def get_policy(policyId):
88 if len(request.args) == 0:
89 if policyId in policy_instances.keys():
90 res = policy_instances[policyId]
91 res["enforceStatus"] = policy_status[policyId]["enforceStatus"]
92 return(res, 200)
93 else:
94 return(set_error(None, "The requested policy does not exist.", 404, None, None, None, "policyId", None))
95 else:
96 return(send_error_code(request.args))
97
98def delete_policy(policyId):
99 if len(request.args) == 0:
100 if policyId in policy_instances.keys():
101 policy_instances.pop(policyId)
102 policy_status.pop(policyId)
103 policy_type_per_instance.pop(policyId)
104 return(None, 204)
105 else:
106 return(set_error(None, "The policy identity does not exist.", 404, "No policy instance has been deleted.", None, None, "policyId", None))
107 else:
108 return(send_error_code(request.args))
109
110def get_policy_status(policyId):
111 if len(request.args) == 0:
112 if policyId in policy_instances.keys():
113 return(policy_status[policyId], 200)
114 else:
115 return(set_error(None, "The policy identity does not exist.", 404, "There is no existing policy instance with the identity: " + policyId, None, None, "policyId", None))
116 else:
117 return(send_error_code(request.args))
118
119def get_all_policytypes_identities():
120 if len(request.args) == 0:
121 return(list(policy_types.keys()), 200)
122 else:
123 return(send_error_code(request.args))
124
125def get_policytypes(policyTypeId):
126 if len(request.args) == 0:
127 if policyTypeId in policy_types.keys():
128 return(policy_types[policyTypeId], 200)
129 else:
130 return(set_error(None, "The requested policy type does not exist.", 404, None, None, None, "policyTypeId", None))
131 else:
132 return(send_error_code(request.args))
133
134def set_error(type_of, title, status, detail, instance, cause, param, reason):
135 error = {}
136 params = {}
137 if type_of is not None:
138 error["type"] = type_of
139 if title is not None:
140 error["title"] = title
141 if status is not None:
142 error["status"] = status
143 if detail is not None:
144 error["detail"] = detail
145 if instance is not None:
146 error["instance"] = instance
147 if cause is not None:
148 error["cause"] = cause
149 if param is not None:
150 params["param"] = param
151 if reason is not None:
152 params["reason"] = reason
153 if params:
154 error["invalidParams"] = params
155 return(error, error["status"])
156
157def send_error_code(args):
158 if 'code' in args.keys():
159 code = args['code']
160 if code == '405':
161 return(set_error(None, "Method not allowed", 405, "Method not allowed for the URI", None, None, None, None))
162 elif code == '429':
163 return(set_error(None, "Too many requests", 429, "Too many requests have been sent in a given amount of time", None, None, None, None))
164 elif code == '507':
165 return(set_error(None, "Insufficient storage", 507, "The method could not be performed on the resource because the provider is unable to store the representation needed to successfully complete the request", None, None, None, None))
166 elif code == '503':
167 return(set_error(None, "Service unavailable", 503, "The provider is currently unable to handle the request due to a temporary overload", None, None, None, None))
168 else:
169 return(set_error(None, "Not found", 400, "No resource found at the URI", None, None, None, None))
170 else:
171 return(set_error(None, "Not found", 400, "No resource found at the URI", None, None, None, None))