From 1100c66ce03a059ebe7ece9734e799b49b3a5a9e Mon Sep 17 00:00:00 2001 From: WuKong Date: Sat, 23 Dec 2017 21:49:35 +0100 Subject: moonv4 cleanup Change-Id: Icef927f3236d985ac13ff7376f6ce6314b2b39b0 Signed-off-by: WuKong --- templates/glance/policy.json | 62 +++ templates/moon_keystone/Dockerfile | 25 + templates/moon_keystone/README.md | 26 + templates/moon_keystone/run.sh | 81 +++ templates/moonforming/Dockerfile | 10 + templates/moonforming/README.md | 12 + templates/moonforming/conf/mls.py | 59 +++ templates/moonforming/conf/rbac.py | 61 +++ templates/moonforming/conf2consul.py | 103 ++++ templates/moonforming/moon.conf | 79 +++ templates/moonforming/populate_default_values.py | 235 +++++++++ templates/moonforming/run.sh | 44 ++ templates/moonforming/utils/__init__.py | 0 templates/moonforming/utils/config.py | 22 + templates/moonforming/utils/models.py | 270 ++++++++++ templates/moonforming/utils/pdp.py | 163 ++++++ templates/moonforming/utils/policies.py | 635 +++++++++++++++++++++++ templates/nova/policy.json | 488 +++++++++++++++++ templates/python_unit_test/Dockerfile | 8 + templates/python_unit_test/README.md | 8 + templates/python_unit_test/requirements.txt | 10 + templates/python_unit_test/run_tests.sh | 13 + 22 files changed, 2414 insertions(+) create mode 100644 templates/glance/policy.json create mode 100644 templates/moon_keystone/Dockerfile create mode 100644 templates/moon_keystone/README.md create mode 100644 templates/moon_keystone/run.sh create mode 100644 templates/moonforming/Dockerfile create mode 100644 templates/moonforming/README.md create mode 100644 templates/moonforming/conf/mls.py create mode 100644 templates/moonforming/conf/rbac.py create mode 100644 templates/moonforming/conf2consul.py create mode 100644 templates/moonforming/moon.conf create mode 100644 templates/moonforming/populate_default_values.py create mode 100644 templates/moonforming/run.sh create mode 100644 templates/moonforming/utils/__init__.py create mode 100644 templates/moonforming/utils/config.py create mode 100644 templates/moonforming/utils/models.py create mode 100644 templates/moonforming/utils/pdp.py create mode 100644 templates/moonforming/utils/policies.py create mode 100644 templates/nova/policy.json create mode 100644 templates/python_unit_test/Dockerfile create mode 100644 templates/python_unit_test/README.md create mode 100644 templates/python_unit_test/requirements.txt create mode 100644 templates/python_unit_test/run_tests.sh (limited to 'templates') diff --git a/templates/glance/policy.json b/templates/glance/policy.json new file mode 100644 index 00000000..5505f67f --- /dev/null +++ b/templates/glance/policy.json @@ -0,0 +1,62 @@ +{ + "context_is_admin": "role:admin", + "default": "role:admin", + + "add_image": "http://my_hostname:31001/authz", + "delete_image": "http://my_hostname:31001/authz", + "get_image": "http://my_hostname:31001/authz", + "get_images": "http://my_hostname:31001/authz", + "modify_image": "http://my_hostname:31001/authz", + "publicize_image": "role:admin", + "communitize_image": "", + "copy_from": "", + + "download_image": "", + "upload_image": "", + + "delete_image_location": "", + "get_image_location": "", + "set_image_location": "", + + "add_member": "", + "delete_member": "", + "get_member": "", + "get_members": "", + "modify_member": "", + + "manage_image_cache": "role:admin", + + "get_task": "role:admin", + "get_tasks": "role:admin", + "add_task": "role:admin", + "modify_task": "role:admin", + + "deactivate": "", + "reactivate": "", + + "get_metadef_namespace": "", + "get_metadef_namespaces":"", + "modify_metadef_namespace":"", + "add_metadef_namespace":"", + + "get_metadef_object":"", + "get_metadef_objects":"", + "modify_metadef_object":"", + "add_metadef_object":"", + + "list_metadef_resource_types":"", + "get_metadef_resource_type":"", + "add_metadef_resource_type_association":"", + + "get_metadef_property":"", + "get_metadef_properties":"", + "modify_metadef_property":"", + "add_metadef_property":"", + + "get_metadef_tag":"", + "get_metadef_tags":"", + "modify_metadef_tag":"", + "add_metadef_tag":"", + "add_metadef_tags":"" + +} diff --git a/templates/moon_keystone/Dockerfile b/templates/moon_keystone/Dockerfile new file mode 100644 index 00000000..2a43bd92 --- /dev/null +++ b/templates/moon_keystone/Dockerfile @@ -0,0 +1,25 @@ +FROM ubuntu:zesty + +ENV ADMIN_TOKEN=p4ssw0rd +ENV ADMIN_PASSWORD=p4ssw0rd +ENV DB_CONNECTION="mysql+pymysql" +ENV DB_DRIVER=sql +ENV DB_HOST=localhost +ENV DB_DATABASE=keystonedb +ENV DB_USER=keystone +ENV DB_PASSWORD=p4ssw0rd +ENV DB_USER_ROOT=root +ENV DB_PASSWORD_ROOT=p4sswOrd1 +ENV RABBIT_NODE=server +ENV INTERFACE_HOST="http://localhost:3001" + +RUN apt update && apt install apache2 rabbitmq-server keystone python-openstackclient libapache2-mod-wsgi mysql-client -y + +# RUN apt update && apt install iputils-ping net-tools -y + +ADD run.sh /root + +EXPOSE 35357 +EXPOSE 5000 + +CMD ["/bin/bash", "/root/run.sh"] \ No newline at end of file diff --git a/templates/moon_keystone/README.md b/templates/moon_keystone/README.md new file mode 100644 index 00000000..7027324e --- /dev/null +++ b/templates/moon_keystone/README.md @@ -0,0 +1,26 @@ +# Keystone container + +## build keystone image + +without proxy: +```bash +docker build -t keystone:mitaka . +``` + +with a proxy: +```bash +docker build --build-arg https_proxy=http://proxy:3128 --build-arg http_proxy=http://proxy:3128 -t keystone:mitaka . +``` + + +### access to the container +```bash +docker container exec -ti keystone /bin/bash +export OS_USERNAME=admin +export OS_PASSWORD=p4ssw0rd +export OS_REGION_NAME=Orange +export OS_TENANT_NAME=admin +export OS_AUTH_URL=http://localhost:5000/v3 +export OS_DOMAIN_NAME=Default +openstack project list +``` \ No newline at end of file diff --git a/templates/moon_keystone/run.sh b/templates/moon_keystone/run.sh new file mode 100644 index 00000000..2a61901e --- /dev/null +++ b/templates/moon_keystone/run.sh @@ -0,0 +1,81 @@ +#!/usr/bin/env bash + +MY_HOSTNAME=localhost + +echo DB_HOST=$DB_HOST +echo DB_DATABASE=$DB_DATABASE +echo RABBIT_NODE=$RABBIT_NODE +echo RABBIT_NODE=$[RABBIT_NODE] +echo INTERFACE_HOST=$INTERFACE_HOST + +sed "s/#admin_token = /admin_token=$ADMIN_TOKEN/g" -i /etc/keystone/keystone.conf +sed "s/#connection = /connection = $DB_CONNECTION:\/\/$DB_USER:$DB_PASSWORD@$DB_HOST\/$DB_DATABASE/g" -i /etc/keystone/keystone.conf + +cat << EOF | tee -a /etc/keystone/keystone.conf +[cors] +allowed_origin = $INTERFACE_HOST +max_age = 3600 +allow_methods = POST,GET,DELETE +EOF + +until echo status | mysql -h${DB_HOST} -u${DB_USER_ROOT} -p${DB_PASSWORD_ROOT}; do + >&2 echo "MySQL is unavailable - sleeping" + sleep 1 +done + +>&2 echo "Mysql is up - executing command" + +mysql -h $DB_HOST -u$DB_USER_ROOT -p$DB_PASSWORD_ROOT < 1 else "consul" + CONSUL_PORT = sys.argv[2] if len(sys.argv) > 2 else 8500 + CONF_FILENAME = sys.argv[3] if len(sys.argv) > 3 else "moon.conf" +HEADERS = {"content-type": "application/json"} + + +def search_config_file(): + data_config = None + for _file in ( + CONF_FILENAME, + "conf/moon.conf", + "../moon.conf", + "../conf/moon.conf", + "/etc/moon/moon.conf", + ): + try: + data_config = yaml.safe_load(open(_file)) + except FileNotFoundError: + data_config = None + continue + else: + break + if not data_config: + raise Exception("Configuration file not found...") + return data_config + + +def put(key, value): + url = "http://{host}:{port}/v1/kv/{key}".format(host=CONSUL_HOST, port=CONSUL_PORT, key=key) + log.info(url) + req = requests.put( + url, + headers=HEADERS, + json=value + ) + if req.status_code != 200: + raise Exception("Error connecting to Consul ({}, {})".format(req.status_code, req.text)) + + +def get(key): + url = "http://{host}:{port}/v1/kv/{key}".format(host=CONSUL_HOST, port=CONSUL_PORT, key=key) + req = requests.get(url) + data = req.json() + for item in data: + log.info("{} {} -> {}".format( + req.status_code, + item["Key"], + json.loads(base64.b64decode(item["Value"]).decode("utf-8")) + )) + yield json.loads(base64.b64decode(item["Value"]).decode("utf-8")) + + +def main(): + data_config = search_config_file() + req = requests.head("http://{}:{}/ui/".format(CONSUL_HOST, CONSUL_PORT)) + if req.status_code != 200: + log.critical("Consul is down...") + log.critical("request info: {}/{}".format(req, req.text)) + sys.exit(1) + + put("database", data_config["database"]) + # put("messenger", data_config["messenger"]) + # put("slave", data_config["slave"]) + # put("docker", data_config["docker"]) + put("logging", data_config["logging"]) + put("components_port_start", data_config["components"]["port_start"]) + + for _key, _value in data_config["components"].items(): + if type(_value) is dict: + put("components/{}".format(_key), data_config["components"][_key]) + + for _key, _value in data_config["plugins"].items(): + put("plugins/{}".format(_key), data_config["plugins"][_key]) + + for _key, _value in data_config["openstack"].items(): + put("openstack/{}".format(_key), data_config["openstack"][_key]) + + +main() + diff --git a/templates/moonforming/moon.conf b/templates/moonforming/moon.conf new file mode 100644 index 00000000..dc498e34 --- /dev/null +++ b/templates/moonforming/moon.conf @@ -0,0 +1,79 @@ +database: + url: mysql+pymysql://moon:p4sswOrd1@db/moon + driver: sql + +openstack: + keystone: + url: http://keystone:5000/v3 + user: admin + password: p4ssw0rd + domain: default + project: admin + check_token: false + certificate: false + +plugins: + authz: + container: wukongsun/moon_authz:v4.3 + port: 8081 + session: + container: asteroide/session:latest + port: 8082 + +components: + interface: + port: 8080 + bind: 0.0.0.0 + hostname: interface + container: wukongsun/moon_interface:v4.3 + orchestrator: + port: 8083 + bind: 0.0.0.0 + hostname: orchestrator + container: wukongsun/moon_orchestrator:v4.3 + wrapper: + port: 8080 + bind: 0.0.0.0 + hostname: wrapper + container: wukongsun/moon_wrapper:v4.3.1 + timeout: 5 + manager: + port: 8082 + bind: 0.0.0.0 + hostname: manager + container: wukongsun/moon_manager:v4.3.1 + port_start: 31001 + +logging: + version: 1 + + formatters: + brief: + format: "%(levelname)s %(name)s %(message)-30s" + custom: + format: "%(asctime)-15s %(levelname)s %(name)s %(message)s" + + handlers: + console: + class : logging.StreamHandler + formatter: brief + level : INFO + stream : ext://sys.stdout + file: + class : logging.handlers.RotatingFileHandler + formatter: custom + level : DEBUG + filename: /tmp/moon.log + maxBytes: 1048576 + backupCount: 3 + + loggers: + moon: + level: DEBUG + handlers: [console, file] + propagate: no + + root: + level: ERROR + handlers: [console] + diff --git a/templates/moonforming/populate_default_values.py b/templates/moonforming/populate_default_values.py new file mode 100644 index 00000000..fa099458 --- /dev/null +++ b/templates/moonforming/populate_default_values.py @@ -0,0 +1,235 @@ +import argparse +import logging +from importlib.machinery import SourceFileLoader +from utils.pdp import * +from utils.models import * +from utils.policies import * + +parser = argparse.ArgumentParser() +parser.add_argument('filename', help='scenario filename', nargs=1) +parser.add_argument("--verbose", "-v", action='store_true', + help="verbose mode") +parser.add_argument("--debug", "-d", action='store_true', help="debug mode") +parser.add_argument("--keystone-pid", "-k", dest="keystone_pid", default="", + help="Force a particular Keystone Project ID") +args = parser.parse_args() + +FORMAT = '%(asctime)-15s %(levelname)s %(message)s' +if args.debug: + logging.basicConfig( + format=FORMAT, + level=logging.DEBUG) +elif args.verbose: + logging.basicConfig( + format=FORMAT, + level=logging.INFO) +else: + logging.basicConfig( + format=FORMAT, + level=logging.WARNING) + +requests_log = logging.getLogger("requests.packages.urllib3") +requests_log.setLevel(logging.WARNING) +requests_log.propagate = True + +logger = logging.getLogger("moonforming") + +if args.filename: + print("Loading: {}".format(args.filename[0])) + +m = SourceFileLoader("scenario", args.filename[0]) + +scenario = m.load_module() + + +def create_model(model_id=None): + if args.verbose: + logger.info("Creating model {}".format(scenario.model_name)) + if not model_id: + logger.info("Add model") + model_id = add_model(name=scenario.model_name) + logger.info("Add subject categories") + for cat in scenario.subject_categories: + scenario.subject_categories[cat] = add_subject_category(name=cat) + logger.info("Add object categories") + for cat in scenario.object_categories: + scenario.object_categories[cat] = add_object_category(name=cat) + logger.info("Add action categories") + for cat in scenario.action_categories: + scenario.action_categories[cat] = add_action_category(name=cat) + sub_cat = [] + ob_cat = [] + act_cat = [] + meta_rule_list = [] + for item_name, item_value in scenario.meta_rule.items(): + for item in item_value["value"]: + if item in scenario.subject_categories: + sub_cat.append(scenario.subject_categories[item]) + elif item in scenario.object_categories: + ob_cat.append(scenario.object_categories[item]) + elif item in scenario.action_categories: + act_cat.append(scenario.action_categories[item]) + meta_rules = check_meta_rule(meta_rule_id=None) + for _meta_rule_id, _meta_rule_value in meta_rules['meta_rules'].items(): + if _meta_rule_value['name'] == item_name: + meta_rule_id = _meta_rule_id + break + else: + logger.info("Add meta rule") + meta_rule_id = add_meta_rule(item_name, sub_cat, ob_cat, act_cat) + item_value["id"] = meta_rule_id + if meta_rule_id not in meta_rule_list: + meta_rule_list.append(meta_rule_id) + return model_id, meta_rule_list + + +def create_policy(model_id, meta_rule_list): + if args.verbose: + logger.info("Creating policy {}".format(scenario.policy_name)) + _policies = check_policy() + for _policy_id, _policy_value in _policies["policies"].items(): + if _policy_value['name'] == scenario.policy_name: + policy_id = _policy_id + break + else: + policy_id = add_policy(name=scenario.policy_name, genre=scenario.policy_genre) + + update_policy(policy_id, model_id) + + for meta_rule_id in meta_rule_list: + logger.debug("add_meta_rule_to_model {} {}".format(model_id, meta_rule_id)) + add_meta_rule_to_model(model_id, meta_rule_id) + + logger.info("Add subject data") + for subject_cat_name in scenario.subject_data: + for subject_data_name in scenario.subject_data[subject_cat_name]: + data_id = scenario.subject_data[subject_cat_name][subject_data_name] = add_subject_data( + policy_id=policy_id, + category_id=scenario.subject_categories[subject_cat_name], name=subject_data_name) + scenario.subject_data[subject_cat_name][subject_data_name] = data_id + logger.info("Add object data") + for object_cat_name in scenario.object_data: + for object_data_name in scenario.object_data[object_cat_name]: + data_id = scenario.object_data[object_cat_name][object_data_name] = add_object_data( + policy_id=policy_id, + category_id=scenario.object_categories[object_cat_name], name=object_data_name) + scenario.object_data[object_cat_name][object_data_name] = data_id + logger.info("Add action data") + for action_cat_name in scenario.action_data: + for action_data_name in scenario.action_data[action_cat_name]: + data_id = scenario.action_data[action_cat_name][action_data_name] = add_action_data( + policy_id=policy_id, + category_id=scenario.action_categories[action_cat_name], name=action_data_name) + scenario.action_data[action_cat_name][action_data_name] = data_id + + logger.info("Add subjects") + for name in scenario.subjects: + scenario.subjects[name] = add_subject(policy_id, name=name) + logger.info("Add objects") + for name in scenario.objects: + scenario.objects[name] = add_object(policy_id, name=name) + logger.info("Add actions") + for name in scenario.actions: + scenario.actions[name] = add_action(policy_id, name=name) + + logger.info("Add subject assignments") + for subject_name in scenario.subject_assignments: + if type(scenario.subject_assignments[subject_name]) in (list, tuple): + for items in scenario.subject_assignments[subject_name]: + for subject_category_name in items: + subject_id = scenario.subjects[subject_name] + subject_cat_id = scenario.subject_categories[subject_category_name] + for data in scenario.subject_assignments[subject_name]: + subject_data_id = scenario.subject_data[subject_category_name][data[subject_category_name]] + add_subject_assignments(policy_id, subject_id, subject_cat_id, subject_data_id) + else: + for subject_category_name in scenario.subject_assignments[subject_name]: + subject_id = scenario.subjects[subject_name] + subject_cat_id = scenario.subject_categories[subject_category_name] + subject_data_id = scenario.subject_data[subject_category_name][scenario.subject_assignments[subject_name][subject_category_name]] + add_subject_assignments(policy_id, subject_id, subject_cat_id, subject_data_id) + + logger.info("Add object assignments") + for object_name in scenario.object_assignments: + if type(scenario.object_assignments[object_name]) in (list, tuple): + for items in scenario.object_assignments[object_name]: + for object_category_name in items: + object_id = scenario.objects[object_name] + object_cat_id = scenario.object_categories[object_category_name] + for data in scenario.object_assignments[object_name]: + object_data_id = scenario.object_data[object_category_name][data[object_category_name]] + add_object_assignments(policy_id, object_id, object_cat_id, object_data_id) + else: + for object_category_name in scenario.object_assignments[object_name]: + object_id = scenario.objects[object_name] + object_cat_id = scenario.object_categories[object_category_name] + object_data_id = scenario.object_data[object_category_name][scenario.object_assignments[object_name][object_category_name]] + add_object_assignments(policy_id, object_id, object_cat_id, object_data_id) + + logger.info("Add action assignments") + for action_name in scenario.action_assignments: + if type(scenario.action_assignments[action_name]) in (list, tuple): + for items in scenario.action_assignments[action_name]: + for action_category_name in items: + action_id = scenario.actions[action_name] + action_cat_id = scenario.action_categories[action_category_name] + for data in scenario.action_assignments[action_name]: + action_data_id = scenario.action_data[action_category_name][data[action_category_name]] + add_action_assignments(policy_id, action_id, action_cat_id, action_data_id) + else: + for action_category_name in scenario.action_assignments[action_name]: + action_id = scenario.actions[action_name] + action_cat_id = scenario.action_categories[action_category_name] + action_data_id = scenario.action_data[action_category_name][scenario.action_assignments[action_name][action_category_name]] + add_action_assignments(policy_id, action_id, action_cat_id, action_data_id) + + logger.info("Add rules") + for meta_rule_name in scenario.rules: + meta_rule_value = scenario.meta_rule[meta_rule_name] + for rule in scenario.rules[meta_rule_name]: + data_list = [] + _meta_rule = list(meta_rule_value["value"]) + for data_name in rule["rule"]: + category_name = _meta_rule.pop(0) + if category_name in scenario.subject_categories: + data_list.append(scenario.subject_data[category_name][data_name]) + elif category_name in scenario.object_categories: + data_list.append(scenario.object_data[category_name][data_name]) + elif category_name in scenario.action_categories: + data_list.append(scenario.action_data[category_name][data_name]) + instructions = rule["instructions"] + add_rule(policy_id, meta_rule_value["id"], data_list, instructions) + return policy_id + + +def create_pdp(policy_id=None): + logger.info("Creating PDP {}".format(scenario.pdp_name)) + projects = get_keystone_projects() + project_id = args.keystone_pid + if not project_id: + for _project in projects['projects']: + if _project['name'] == "admin": + project_id = _project['id'] + assert project_id + pdps = check_pdp()["pdps"] + for pdp_id, pdp_value in pdps.items(): + if scenario.pdp_name == pdp_value["name"]: + update_pdp(pdp_id, policy_id=policy_id) + logger.debug("Found existing PDP named {} (will add policy {})".format(scenario.pdp_name, policy_id)) + return pdp_id + _pdp_id = add_pdp(name=scenario.pdp_name, policy_id=policy_id) + map_to_keystone(pdp_id=_pdp_id, keystone_project_id=project_id) + return _pdp_id + +if __name__ == "__main__": + _models = check_model() + for _model_id, _model_value in _models['models'].items(): + if _model_value['name'] == scenario.model_name: + model_id = _model_id + meta_rule_list = _model_value['meta_rules'] + create_model(model_id) + break + else: + model_id, meta_rule_list = create_model() + policy_id = create_policy(model_id, meta_rule_list) + pdp_id = create_pdp(policy_id) diff --git a/templates/moonforming/run.sh b/templates/moonforming/run.sh new file mode 100644 index 00000000..71543f9e --- /dev/null +++ b/templates/moonforming/run.sh @@ -0,0 +1,44 @@ +#!/usr/bin/env bash + +populate_args=$* + +echo "Waiting for Consul (http://consul:8500)" +while ! python -c "import requests; req = requests.get('http://consul:8500')" 2>/dev/null ; do + sleep 5 ; + echo "." +done + +echo "Consul (http://consul:8500) is up." + +python3 /root/conf2consul.py /etc/moon/moon.conf + +echo "Waiting for DB (tcp://db:3306)" +while ! python -c "import socket, sys; s = socket.socket(socket.AF_INET, socket.SOCK_STREAM); s.connect(('db', 3306)); sys.exit(0)" 2>/dev/null ; do + sleep 5 ; + echo "." +done + +echo "Database (http://db:3306) is up." + +moon_db_manager upgrade + +echo "Waiting for Keystone (http://keystone:5000)" +while ! python -c "import requests; req = requests.get('http://keystone:5000')" 2>/dev/null ; do + sleep 5 ; + echo "." +done + +echo "Keystone (http://keystone:5000) is up." + +echo "Waiting for Manager (http://manager:8082)" +while ! python -c "import requests; req = requests.get('http://manager:8082')" 2>/dev/null ; do + sleep 5 ; + echo "." +done + +echo "Manager (http://manager:8082) is up." + +cd /root + +python3 populate_default_values.py $populate_args /root/conf/rbac.py +python3 populate_default_values.py $populate_args /root/conf/mls.py diff --git a/templates/moonforming/utils/__init__.py b/templates/moonforming/utils/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/templates/moonforming/utils/config.py b/templates/moonforming/utils/config.py new file mode 100644 index 00000000..30c8ea4f --- /dev/null +++ b/templates/moonforming/utils/config.py @@ -0,0 +1,22 @@ +import yaml + + +def get_config_data(filename="moon.conf"): + data_config = None + for _file in ( + filename, + "conf/moon.conf", + "../moon.conf", + "../conf/moon.conf", + "/etc/moon/moon.conf", + ): + try: + data_config = yaml.safe_load(open(_file)) + except FileNotFoundError: + data_config = None + continue + else: + break + if not data_config: + raise Exception("Configuration file not found...") + return data_config diff --git a/templates/moonforming/utils/models.py b/templates/moonforming/utils/models.py new file mode 100644 index 00000000..3cf31354 --- /dev/null +++ b/templates/moonforming/utils/models.py @@ -0,0 +1,270 @@ +import requests +import copy +import utils.config + +config = utils.config.get_config_data() + +URL = "http://{}:{}".format( + config['components']['manager']['hostname'], + config['components']['manager']['port']) +URL = URL + "{}" +HEADERS = {"content-type": "application/json"} + +model_template = { + "name": "test_model", + "description": "test", + "meta_rules": [] +} + +category_template = { + "name": "name of the category", + "description": "description of the category" +} + +meta_rule_template = { + "name": "test_meta_rule", + "subject_categories": [], + "object_categories": [], + "action_categories": [] +} + + +def check_model(model_id=None, check_model_name=True): + req = requests.get(URL.format("/models")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "models" in result + if model_id: + assert result["models"] + assert model_id in result['models'] + assert "name" in result['models'][model_id] + if check_model_name: + assert model_template["name"] == result['models'][model_id]["name"] + return result + + +def add_model(name=None): + if name: + model_template['name'] = name + req = requests.post(URL.format("/models"), json=model_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + model_id = list(result['models'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['models'][model_id] + assert model_template["name"] == result['models'][model_id]["name"] + return model_id + + +def delete_model(model_id): + req = requests.delete(URL.format("/models/{}".format(model_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + + +def add_subject_category(name="subject_cat_1"): + category_template["name"] = name + req = requests.post(URL.format("/subject_categories"), json=category_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "subject_categories" in result + category_id = list(result['subject_categories'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['subject_categories'][category_id] + assert category_template["name"] == result['subject_categories'][category_id]["name"] + return category_id + + +def check_subject_category(category_id): + req = requests.get(URL.format("/subject_categories")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "subject_categories" in result + if "result" in result: + assert result["result"] + assert category_id in result['subject_categories'] + assert "name" in result['subject_categories'][category_id] + assert category_template["name"] == result['subject_categories'][category_id]["name"] + + +def delete_subject_category(category_id): + req = requests.delete(URL.format("/subject_categories/{}".format(category_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + if "result" in result: + assert result["result"] + + +def add_object_category(name="object_cat_1"): + category_template["name"] = name + req = requests.post(URL.format("/object_categories"), json=category_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "object_categories" in result + category_id = list(result['object_categories'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['object_categories'][category_id] + assert category_template["name"] == result['object_categories'][category_id]["name"] + return category_id + + +def check_object_category(category_id): + req = requests.get(URL.format("/object_categories")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "object_categories" in result + if "result" in result: + assert result["result"] + assert category_id in result['object_categories'] + assert "name" in result['object_categories'][category_id] + assert category_template["name"] == result['object_categories'][category_id]["name"] + + +def delete_object_category(category_id): + req = requests.delete(URL.format("/object_categories/{}".format(category_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + if "result" in result: + assert result["result"] + + +def add_action_category(name="action_cat_1"): + category_template["name"] = name + req = requests.post(URL.format("/action_categories"), json=category_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "action_categories" in result + category_id = list(result['action_categories'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['action_categories'][category_id] + assert category_template["name"] == result['action_categories'][category_id]["name"] + return category_id + + +def check_action_category(category_id): + req = requests.get(URL.format("/action_categories")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "action_categories" in result + if "result" in result: + assert result["result"] + assert category_id in result['action_categories'] + assert "name" in result['action_categories'][category_id] + assert category_template["name"] == result['action_categories'][category_id]["name"] + + +def delete_action_category(category_id): + req = requests.delete(URL.format("/action_categories/{}".format(category_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + if "result" in result: + assert result["result"] + + +def add_categories_and_meta_rule(name="test_meta_rule"): + scat_id = add_subject_category() + ocat_id = add_object_category() + acat_id = add_action_category() + _meta_rule_template = copy.deepcopy(meta_rule_template) + _meta_rule_template["name"] = name + _meta_rule_template["subject_categories"].append(scat_id) + _meta_rule_template["object_categories"].append(ocat_id) + _meta_rule_template["action_categories"].append(acat_id) + req = requests.post(URL.format("/meta_rules"), json=_meta_rule_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "meta_rules" in result + meta_rule_id = list(result['meta_rules'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['meta_rules'][meta_rule_id] + assert _meta_rule_template["name"] == result['meta_rules'][meta_rule_id]["name"] + return meta_rule_id, scat_id, ocat_id, acat_id + + +def add_meta_rule(name="test_meta_rule", scat=[], ocat=[], acat=[]): + _meta_rule_template = copy.deepcopy(meta_rule_template) + _meta_rule_template["name"] = name + _meta_rule_template["subject_categories"] = [] + _meta_rule_template["subject_categories"].extend(scat) + _meta_rule_template["object_categories"] = [] + _meta_rule_template["object_categories"].extend(ocat) + _meta_rule_template["action_categories"] = [] + _meta_rule_template["action_categories"].extend(acat) + req = requests.post(URL.format("/meta_rules"), json=_meta_rule_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "meta_rules" in result + meta_rule_id = list(result['meta_rules'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['meta_rules'][meta_rule_id] + assert _meta_rule_template["name"] == result['meta_rules'][meta_rule_id]["name"] + return meta_rule_id + + +def check_meta_rule(meta_rule_id, scat_id=None, ocat_id=None, acat_id=None): + req = requests.get(URL.format("/meta_rules")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "meta_rules" in result + if "result" in result: + assert result["result"] + if not meta_rule_id: + return result + assert meta_rule_id in result['meta_rules'] + assert "name" in result['meta_rules'][meta_rule_id] + if scat_id: + assert scat_id in result['meta_rules'][meta_rule_id]["subject_categories"] + if ocat_id: + assert ocat_id in result['meta_rules'][meta_rule_id]["object_categories"] + if acat_id: + assert acat_id in result['meta_rules'][meta_rule_id]["action_categories"] + + +def delete_meta_rule(meta_rule_id): + req = requests.delete(URL.format("/meta_rules/{}".format(meta_rule_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + if "result" in result: + assert result["result"] + + +def add_meta_rule_to_model(model_id, meta_rule_id): + model = check_model(model_id, check_model_name=False)['models'] + meta_rule_list = model[model_id]["meta_rules"] + if meta_rule_id not in meta_rule_list: + meta_rule_list.append(meta_rule_id) + req = requests.patch(URL.format("/models/{}".format(model_id)), + json={"meta_rules": meta_rule_list}, + headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + model_id = list(result['models'].keys())[0] + if "result" in result: + assert result["result"] + assert "meta_rules" in result['models'][model_id] + assert meta_rule_list == result['models'][model_id]["meta_rules"] diff --git a/templates/moonforming/utils/pdp.py b/templates/moonforming/utils/pdp.py new file mode 100644 index 00000000..f3c6df37 --- /dev/null +++ b/templates/moonforming/utils/pdp.py @@ -0,0 +1,163 @@ +import logging +import requests +import utils.config + +config = utils.config.get_config_data() +logger = logging.getLogger("moonforming.utils.policies") + +URL = "http://{}:{}".format( + config['components']['manager']['hostname'], + config['components']['manager']['port']) +HEADERS = {"content-type": "application/json"} +KEYSTONE_USER = config['openstack']['keystone']['user'] +KEYSTONE_PASSWORD = config['openstack']['keystone']['password'] +KEYSTONE_PROJECT = config['openstack']['keystone']['project'] +KEYSTONE_SERVER = config['openstack']['keystone']['url'] + +pdp_template = { + "name": "test_pdp", + "security_pipeline": [], + "keystone_project_id": None, + "description": "test", +} + + +def get_keystone_projects(): + + HEADERS = { + "Content-Type": "application/json" + } + + data_auth = { + "auth": { + "identity": { + "methods": [ + "password" + ], + "password": { + "user": { + "name": KEYSTONE_USER, + "domain": { + "name": "Default" + }, + "password": KEYSTONE_PASSWORD + } + } + } + } + } + + req = requests.post("{}/auth/tokens".format(KEYSTONE_SERVER), json=data_auth, headers=HEADERS) + logger.debug("{}/auth/tokens".format(KEYSTONE_SERVER)) + logger.debug(req.text) + assert req.status_code in (200, 201) + TOKEN = req.headers['X-Subject-Token'] + HEADERS['X-Auth-Token'] = TOKEN + req = requests.get("{}/projects".format(KEYSTONE_SERVER), headers=HEADERS) + if req.status_code not in (200, 201): + data_auth["auth"]["scope"] = { + "project": { + "name": KEYSTONE_PROJECT, + "domain": { + "id": "default" + } + } + } + req = requests.post("{}/auth/tokens".format(KEYSTONE_SERVER), json=data_auth, headers=HEADERS) + assert req.status_code in (200, 201) + TOKEN = req.headers['X-Subject-Token'] + HEADERS['X-Auth-Token'] = TOKEN + req = requests.get("{}/projects".format(KEYSTONE_SERVER), headers=HEADERS) + assert req.status_code in (200, 201) + return req.json() + + +def check_pdp(pdp_id=None, keystone_project_id=None, moon_url=None): + _URL = URL + if moon_url: + _URL = moon_url + req = requests.get(_URL + "/pdp") + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "pdps" in result + if pdp_id: + assert result["pdps"] + assert pdp_id in result['pdps'] + assert "name" in result['pdps'][pdp_id] + assert pdp_template["name"] == result['pdps'][pdp_id]["name"] + if keystone_project_id: + assert result["pdps"] + assert pdp_id in result['pdps'] + assert "keystone_project_id" in result['pdps'][pdp_id] + assert keystone_project_id == result['pdps'][pdp_id]["keystone_project_id"] + return result + + +def add_pdp(name="test_pdp", policy_id=None): + pdp_template['name'] = name + if policy_id: + pdp_template['security_pipeline'].append(policy_id) + req = requests.post(URL + "/pdp", json=pdp_template, headers=HEADERS) + logger.debug(req.status_code) + logger.debug(req) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + pdp_id = list(result['pdps'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['pdps'][pdp_id] + assert pdp_template["name"] == result['pdps'][pdp_id]["name"] + return pdp_id + + +def update_pdp(pdp_id, policy_id=None): + req = requests.get(URL + "/pdp/{}".format(pdp_id)) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "pdps" in result + assert pdp_id in result['pdps'] + pipeline = result['pdps'][pdp_id]["security_pipeline"] + if policy_id not in pipeline: + pipeline.append(policy_id) + req = requests.patch(URL + "/pdp/{}".format(pdp_id), + json={"security_pipeline": pipeline}) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "pdps" in result + assert pdp_id in result['pdps'] + + req = requests.get(URL + "/pdp/{}".format(pdp_id)) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "pdps" in result + assert pdp_id in result['pdps'] + assert policy_id in pipeline + + +def map_to_keystone(pdp_id, keystone_project_id): + req = requests.patch(URL + "/pdp/{}".format(pdp_id), json={"keystone_project_id": keystone_project_id}, + headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + if "result" in result: + assert result["result"] + assert pdp_id in result['pdps'] + assert "name" in result['pdps'][pdp_id] + assert pdp_template["name"] == result['pdps'][pdp_id]["name"] + return pdp_id + + +def delete_pdp(pdp_id): + req = requests.delete(URL + "/pdp/{}".format(pdp_id)) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + diff --git a/templates/moonforming/utils/policies.py b/templates/moonforming/utils/policies.py new file mode 100644 index 00000000..bd08291a --- /dev/null +++ b/templates/moonforming/utils/policies.py @@ -0,0 +1,635 @@ +import logging +import requests +import utils.config + +config = utils.config.get_config_data() +logger = logging.getLogger("moonforming.utils.policies") + +URL = "http://{}:{}".format(config['components']['manager']['hostname'], config['components']['manager']['port']) +URL = URL + "{}" +HEADERS = {"content-type": "application/json"} +FILE = open("/tmp/test.log", "w") + +policy_template = { + "name": "test_policy", + "model_id": "", + "genre": "authz", + "description": "test", +} + +subject_template = { + "name": "test_subject", + "description": "test", + "email": "mail", + "password": "my_pass", +} + +object_template = { + "name": "test_subject", + "description": "test" +} + +action_template = { + "name": "test_subject", + "description": "test" +} + +subject_data_template = { + "name": "subject_data1", + "description": "description of the data subject" +} + +object_data_template = { + "name": "object_data1", + "description": "description of the data subject" +} + +action_data_template = { + "name": "action_data1", + "description": "description of the data subject" +} + +subject_assignment_template = { + "id": "", + "category_id": "", + "scope_id": "" +} + + +def check_policy(policy_id=None): + req = requests.get(URL.format("/policies")) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "policies" in result + if policy_id: + assert result["policies"] + assert policy_id in result['policies'] + assert "name" in result['policies'][policy_id] + assert policy_template["name"] == result['policies'][policy_id]["name"] + return result + + +def add_policy(name="test_policy", genre="authz"): + policy_template["name"] = name + policy_template["genre"] = genre + req = requests.post(URL.format("/policies"), json=policy_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + policy_id = list(result['policies'].keys())[0] + if "result" in result: + assert result["result"] + assert "name" in result['policies'][policy_id] + assert policy_template["name"] == result['policies'][policy_id]["name"] + return policy_id + + +def update_policy(policy_id, model_id): + req = requests.patch(URL.format("/policies/{}".format(policy_id)), + json={"model_id": model_id}, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + policy_id = list(result['policies'].keys())[0] + if "result" in result: + assert result["result"] + assert "model_id" in result['policies'][policy_id] + assert model_id == result['policies'][policy_id]["model_id"] + + +def delete_policy(policy_id): + req = requests.delete(URL.format("/policies/{}".format(policy_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + + +def add_subject(policy_id=None, name="test_subject"): + subject_template['name'] = name + if policy_id: + logger.debug(URL.format("/policies/{}/subjects".format(policy_id))) + req = requests.post(URL.format("/policies/{}/subjects".format(policy_id)), + json=subject_template, headers=HEADERS) + else: + logger.debug(URL.format("/subjects")) + req = requests.post(URL.format("/subjects"), json=subject_template, headers=HEADERS) + logger.debug(req.text) + assert req.status_code == 200 + result = req.json() + assert "subjects" in result + subject_id = list(result['subjects'].keys())[0] + return subject_id + + +def update_subject(subject_id, policy_id=None, description=None): + if policy_id and not description: + req = requests.patch(URL.format("/policies/{}/subjects/{}".format(policy_id, subject_id)), + json={}) + elif policy_id and description: + req = requests.patch(URL.format("/policies/{}/subjects/{}".format(policy_id, subject_id)), + json={"description": description}) + else: + req = requests.patch(URL.format("/subjects/{}".format(subject_id)), + json={"description": description}) + assert req.status_code == 200 + result = req.json() + assert "subjects" in result + assert "name" in result["subjects"][subject_id] + assert subject_template["name"] == result["subjects"][subject_id]["name"] + assert "policy_list" in result["subjects"][subject_id] + if policy_id: + assert policy_id in result["subjects"][subject_id]["policy_list"] + if description: + assert description in result["subjects"][subject_id]["description"] + + +def check_subject(subject_id=None, policy_id=None): + if policy_id: + req = requests.get(URL.format("/policies/{}/subjects".format(policy_id))) + else: + req = requests.get(URL.format("/subjects")) + assert req.status_code == 200 + result = req.json() + assert "subjects" in result + assert "name" in result["subjects"][subject_id] + assert subject_template["name"] == result["subjects"][subject_id]["name"] + if policy_id: + assert "policy_list" in result["subjects"][subject_id] + assert policy_id in result["subjects"][subject_id]["policy_list"] + + +def delete_subject(subject_id, policy_id=None): + if policy_id: + req = requests.delete(URL.format("/policies/{}/subjects/{}".format(policy_id, subject_id))) + else: + req = requests.delete(URL.format("/subjects/{}".format(subject_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + + if policy_id: + req = requests.get(URL.format("/policies/{}/subjects".format(policy_id))) + else: + req = requests.get(URL.format("/subjects")) + assert req.status_code == 200 + result = req.json() + assert "subjects" in result + if subject_id in result["subjects"]: + assert "name" in result["subjects"][subject_id] + assert subject_template["name"] == result["subjects"][subject_id]["name"] + if policy_id: + assert "policy_list" in result["subjects"][subject_id] + assert policy_id not in result["subjects"][subject_id]["policy_list"] + + +def add_object(policy_id=None, name="test_object"): + object_template['name'] = name + if policy_id: + req = requests.post(URL.format("/policies/{}/objects".format(policy_id)), + json=object_template, headers=HEADERS) + else: + req = requests.post(URL.format("/objects"), json=object_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "objects" in result + object_id = list(result['objects'].keys())[0] + return object_id + + +def update_object(object_id, policy_id): + req = requests.patch(URL.format("/policies/{}/objects/{}".format(policy_id, object_id)), json={}) + assert req.status_code == 200 + result = req.json() + assert "objects" in result + assert "name" in result["objects"][object_id] + assert object_template["name"] == result["objects"][object_id]["name"] + assert "policy_list" in result["objects"][object_id] + assert policy_id in result["objects"][object_id]["policy_list"] + + +def check_object(object_id=None, policy_id=None): + if policy_id: + req = requests.get(URL.format("/policies/{}/objects".format(policy_id))) + else: + req = requests.get(URL.format("/objects")) + assert req.status_code == 200 + result = req.json() + assert "objects" in result + assert "name" in result["objects"][object_id] + assert object_template["name"] == result["objects"][object_id]["name"] + if policy_id: + assert "policy_list" in result["objects"][object_id] + assert policy_id in result["objects"][object_id]["policy_list"] + + +def delete_object(object_id, policy_id=None): + if policy_id: + req = requests.delete(URL.format("/policies/{}/objects/{}".format(policy_id, object_id))) + else: + req = requests.delete(URL.format("/objects/{}".format(object_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + + if policy_id: + req = requests.get(URL.format("/policies/{}/objects".format(policy_id))) + else: + req = requests.get(URL.format("/objects")) + assert req.status_code == 200 + result = req.json() + assert "objects" in result + if object_id in result["objects"]: + assert "name" in result["objects"][object_id] + assert object_template["name"] == result["objects"][object_id]["name"] + if policy_id: + assert "policy_list" in result["objects"][object_id] + assert policy_id not in result["objects"][object_id]["policy_list"] + + +def add_action(policy_id=None, name="test_action"): + action_template['name'] = name + if policy_id: + req = requests.post(URL.format("/policies/{}/actions".format(policy_id)), + json=action_template, headers=HEADERS) + else: + req = requests.post(URL.format("/actions"), json=action_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "actions" in result + action_id = list(result['actions'].keys())[0] + return action_id + + +def update_action(action_id, policy_id): + req = requests.patch(URL.format("/policies/{}/actions/{}".format(policy_id, action_id)), json={}) + assert req.status_code == 200 + result = req.json() + assert "actions" in result + assert "name" in result["actions"][action_id] + assert action_template["name"] == result["actions"][action_id]["name"] + assert "policy_list" in result["actions"][action_id] + assert policy_id in result["actions"][action_id]["policy_list"] + + +def check_action(action_id=None, policy_id=None): + if policy_id: + req = requests.get(URL.format("/policies/{}/actions".format(policy_id))) + else: + req = requests.get(URL.format("/actions")) + assert req.status_code == 200 + result = req.json() + assert "actions" in result + assert "name" in result["actions"][action_id] + assert action_template["name"] == result["actions"][action_id]["name"] + if policy_id: + assert "policy_list" in result["actions"][action_id] + assert policy_id in result["actions"][action_id]["policy_list"] + + +def delete_action(action_id, policy_id=None): + if policy_id: + req = requests.delete(URL.format("/policies/{}/actions/{}".format(policy_id, action_id))) + else: + req = requests.delete(URL.format("/actions/{}".format(action_id))) + assert req.status_code == 200 + result = req.json() + assert type(result) is dict + assert "result" in result + assert result["result"] + + if policy_id: + req = requests.get(URL.format("/policies/{}/actions".format(policy_id))) + else: + req = requests.get(URL.format("/actions")) + assert req.status_code == 200 + result = req.json() + assert "actions" in result + if action_id in result["actions"]: + assert "name" in result["actions"][action_id] + assert action_template["name"] == result["actions"][action_id]["name"] + if policy_id: + assert "policy_list" in result["actions"][action_id] + assert policy_id not in result["actions"][action_id]["policy_list"] + + +def add_subject_data(policy_id, category_id, name="subject_data1"): + subject_data_template['name'] = name + req = requests.post(URL.format("/policies/{}/subject_data/{}".format(policy_id, category_id)), + json=subject_data_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "subject_data" in result + subject_id = list(result['subject_data']['data'].keys())[0] + return subject_id + + +def check_subject_data(policy_id, data_id, category_id): + req = requests.get(URL.format("/policies/{}/subject_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "subject_data" in result + for _data in result['subject_data']: + assert data_id in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def delete_subject_data(policy_id, category_id, data_id): + req = requests.delete(URL.format("/policies/{}/subject_data/{}/{}".format(policy_id, category_id, data_id)), + headers=HEADERS) + assert req.status_code == 200 + req = requests.get(URL.format("/policies/{}/subject_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "subject_data" in result + for _data in result['subject_data']: + assert data_id not in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def add_object_data(policy_id, category_id, name="object_data1"): + object_data_template['name'] = name + req = requests.post(URL.format("/policies/{}/object_data/{}".format(policy_id, category_id)), + json=object_data_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "object_data" in result + object_id = list(result['object_data']['data'].keys())[0] + return object_id + + +def check_object_data(policy_id, data_id, category_id): + req = requests.get(URL.format("/policies/{}/object_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "object_data" in result + for _data in result['object_data']: + assert data_id in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def delete_object_data(policy_id, category_id, data_id): + req = requests.delete(URL.format("/policies/{}/object_data/{}/{}".format(policy_id, category_id, data_id)), + headers=HEADERS) + assert req.status_code == 200 + req = requests.get(URL.format("/policies/{}/object_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "object_data" in result + for _data in result['object_data']: + assert data_id not in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def add_action_data(policy_id, category_id, name="action_data1"): + action_data_template['name'] = name + req = requests.post(URL.format("/policies/{}/action_data/{}".format(policy_id, category_id)), + json=action_data_template, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "action_data" in result + action_id = list(result['action_data']['data'].keys())[0] + return action_id + + +def check_action_data(policy_id, data_id, category_id): + req = requests.get(URL.format("/policies/{}/action_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "action_data" in result + for _data in result['action_data']: + assert data_id in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def delete_action_data(policy_id, category_id, data_id): + req = requests.delete(URL.format("/policies/{}/action_data/{}/{}".format(policy_id, category_id, data_id)), + headers=HEADERS) + assert req.status_code == 200 + req = requests.get(URL.format("/policies/{}/action_data/{}".format(policy_id, category_id))) + assert req.status_code == 200 + result = req.json() + assert "action_data" in result + for _data in result['action_data']: + assert data_id not in list(_data['data'].keys()) + assert category_id == _data["category_id"] + + +def add_subject_assignments(policy_id, subject_id, subject_cat_id, subject_data_id): + req = requests.post(URL.format("/policies/{}/subject_assignments".format(policy_id)), + json={ + "id": subject_id, + "category_id": subject_cat_id, + "data_id": subject_data_id + }, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "subject_assignments" in result + assert result["subject_assignments"] + + +def check_subject_assignments(policy_id, subject_id, subject_cat_id, subject_data_id): + req = requests.get(URL.format("/policies/{}/subject_assignments/{}/{}/{}".format( + policy_id, subject_id, subject_cat_id, subject_data_id))) + assert req.status_code == 200 + result = req.json() + assert "subject_assignments" in result + assert result["subject_assignments"] + for key in result["subject_assignments"]: + assert "subject_id" in result["subject_assignments"][key] + assert "category_id" in result["subject_assignments"][key] + assert "assignments" in result["subject_assignments"][key] + if result["subject_assignments"][key]['subject_id'] == subject_id and \ + result["subject_assignments"][key]["category_id"] == subject_cat_id: + assert subject_data_id in result["subject_assignments"][key]["assignments"] + + +def check_object_assignments(policy_id, object_id, object_cat_id, object_data_id): + req = requests.get(URL.format("/policies/{}/object_assignments/{}/{}/{}".format( + policy_id, object_id, object_cat_id, object_data_id))) + assert req.status_code == 200 + result = req.json() + assert "object_assignments" in result + assert result["object_assignments"] + for key in result["object_assignments"]: + assert "object_id" in result["object_assignments"][key] + assert "category_id" in result["object_assignments"][key] + assert "assignments" in result["object_assignments"][key] + if result["object_assignments"][key]['object_id'] == object_id and \ + result["object_assignments"][key]["category_id"] == object_cat_id: + assert object_data_id in result["object_assignments"][key]["assignments"] + + +def check_action_assignments(policy_id, action_id, action_cat_id, action_data_id): + req = requests.get(URL.format("/policies/{}/action_assignments/{}/{}/{}".format( + policy_id, action_id, action_cat_id, action_data_id))) + assert req.status_code == 200 + result = req.json() + assert "action_assignments" in result + assert result["action_assignments"] + for key in result["action_assignments"]: + assert "action_id" in result["action_assignments"][key] + assert "category_id" in result["action_assignments"][key] + assert "assignments" in result["action_assignments"][key] + if result["action_assignments"][key]['action_id'] == action_id and \ + result["action_assignments"][key]["category_id"] == action_cat_id: + assert action_data_id in result["action_assignments"][key]["assignments"] + + +def add_object_assignments(policy_id, object_id, object_cat_id, object_data_id): + req = requests.post(URL.format("/policies/{}/object_assignments".format(policy_id)), + json={ + "id": object_id, + "category_id": object_cat_id, + "data_id": object_data_id + }, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "object_assignments" in result + assert result["object_assignments"] + + +def add_action_assignments(policy_id, action_id, action_cat_id, action_data_id): + req = requests.post(URL.format("/policies/{}/action_assignments".format(policy_id)), + json={ + "id": action_id, + "category_id": action_cat_id, + "data_id": action_data_id + }, headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "action_assignments" in result + assert result["action_assignments"] + + +def delete_subject_assignment(policy_id, subject_id, subject_cat_id, subject_data_id): + req = requests.delete(URL.format("/policies/{}/subject_assignments/{}/{}/{}".format( + policy_id, subject_id, subject_cat_id, subject_data_id))) + assert req.status_code == 200 + result = req.json() + assert "result" in result + assert result["result"] + + req = requests.get(URL.format("/policies/{}/subject_assignments/{}/{}/{}".format( + policy_id, subject_id, subject_cat_id, subject_data_id))) + assert req.status_code == 200 + result = req.json() + assert "subject_assignments" in result + assert result["subject_assignments"] + for key in result["subject_assignments"]: + assert "subject_id" in result["subject_assignments"][key] + assert "category_id" in result["subject_assignments"][key] + assert "assignments" in result["subject_assignments"][key] + if result["subject_assignments"][key]['subject_id'] == subject_id and \ + result["subject_assignments"][key]["category_id"] == subject_cat_id: + assert subject_data_id not in result["subject_assignments"][key]["assignments"] + + +def delete_object_assignment(policy_id, object_id, object_cat_id, object_data_id): + req = requests.delete(URL.format("/policies/{}/object_assignments/{}/{}/{}".format( + policy_id, object_id, object_cat_id, object_data_id))) + assert req.status_code == 200 + result = req.json() + assert "result" in result + assert result["result"] + + req = requests.get(URL.format("/policies/{}/object_assignments/{}/{}/{}".format( + policy_id, object_id, object_cat_id, object_data_id))) + assert req.status_code == 200 + result = req.json() + assert "object_assignments" in result + assert result["object_assignments"] + for key in result["object_assignments"]: + assert "object_id" in result["object_assignments"][key] + assert "category_id" in result["object_assignments"][key] + assert "assignments" in result["object_assignments"][key] + if result["object_assignments"][key]['object_id'] == object_id and \ + result["object_assignments"][key]["category_id"] == object_cat_id: + assert object_data_id not in result["object_assignments"][key]["assignments"] + + +def delete_action_assignment(policy_id, action_id, action_cat_id, action_data_id): + req = requests.delete(URL.format("/policies/{}/action_assignments/{}/{}/{}".format( + policy_id, action_id, action_cat_id, action_data_id))) + assert req.status_code == 200 + result = req.json() + assert "result" in result + assert result["result"] + + req = requests.get(URL.format("/policies/{}/action_assignments/{}/{}/{}".format( + policy_id, action_id, action_cat_id, action_data_id))) + assert req.status_code == 200 + result = req.json() + assert "action_assignments" in result + assert result["action_assignments"] + for key in result["action_assignments"]: + assert "action_id" in result["action_assignments"][key] + assert "category_id" in result["action_assignments"][key] + assert "assignments" in result["action_assignments"][key] + if result["action_assignments"][key]['action_id'] == action_id and \ + result["action_assignments"][key]["category_id"] == action_cat_id: + assert action_data_id not in result["action_assignments"][key]["assignments"] + + +def add_rule(policy_id, meta_rule_id, rule, instructions={"chain": [{"security_pipeline": "rbac"}]}): + req = requests.post(URL.format("/policies/{}/rules".format(policy_id)), + json={ + "meta_rule_id": meta_rule_id, + "rule": rule, + "instructions": instructions, + "enabled": True + }, + headers=HEADERS) + assert req.status_code == 200 + result = req.json() + assert "rules" in result + try: + rule_id = list(result["rules"].keys())[0] + except Exception as e: + return False + assert "policy_id" in result["rules"][rule_id] + assert policy_id == result["rules"][rule_id]["policy_id"] + assert "meta_rule_id" in result["rules"][rule_id] + assert meta_rule_id == result["rules"][rule_id]["meta_rule_id"] + assert rule == result["rules"][rule_id]["rule"] + return rule_id + + +def check_rule(policy_id, meta_rule_id, rule_id, rule): + req = requests.get(URL.format("/policies/{}/rules".format(policy_id))) + assert req.status_code == 200 + result = req.json() + assert "rules" in result + assert "policy_id" in result["rules"] + assert policy_id == result["rules"]["policy_id"] + for item in result["rules"]["rules"]: + assert "meta_rule_id" in item + if meta_rule_id == item["meta_rule_id"]: + if rule_id == item["id"]: + assert rule == item["rule"] + + +def delete_rule(policy_id, rule_id): + req = requests.delete(URL.format("/policies/{}/rules/{}".format(policy_id, rule_id))) + assert req.status_code == 200 + result = req.json() + assert "result" in result + assert result["result"] + + req = requests.get(URL.format("/policies/{}/rules".format(policy_id))) + assert req.status_code == 200 + result = req.json() + assert "rules" in result + assert "policy_id" in result["rules"] + assert policy_id == result["rules"]["policy_id"] + found_rule = False + for item in result["rules"]["rules"]: + if rule_id == item["id"]: + found_rule = True + assert not found_rule diff --git a/templates/nova/policy.json b/templates/nova/policy.json new file mode 100644 index 00000000..29763ce3 --- /dev/null +++ b/templates/nova/policy.json @@ -0,0 +1,488 @@ +{ + "context_is_admin": "role:admin", + "admin_or_owner": "is_admin:True or project_id:%(project_id)s", + "default": "rule:admin_or_owner", + + "cells_scheduler_filter:TargetCellFilter": "is_admin:True", + + "compute:create": "http://my_hostname:31001/authz", + "compute:create:attach_network": "", + "compute:create:attach_volume": "", + "compute:create:forced_host": "is_admin:True", + + "compute:get": "http://my_hostname:31001/authz", + "compute:get_all": "http://my_hostname:31001/authz", + "compute:get_all_tenants": "is_admin:True", + + "compute:update": "", + + "compute:get_instance_metadata": "", + "compute:get_all_instance_metadata": "", + "compute:get_all_instance_system_metadata": "", + "compute:update_instance_metadata": "", + "compute:delete_instance_metadata": "", + + "compute:get_instance_faults": "", + "compute:get_diagnostics": "", + "compute:get_instance_diagnostics": "", + + "compute:start": "rule:admin_or_owner", + "compute:stop": "rule:admin_or_owner", + + "compute:get_lock": "", + "compute:lock": "rule:admin_or_owner", + "compute:unlock": "rule:admin_or_owner", + "compute:unlock_override": "rule:admin_api", + + "compute:get_vnc_console": "", + "compute:get_spice_console": "", + "compute:get_rdp_console": "", + "compute:get_serial_console": "", + "compute:get_mks_console": "", + "compute:get_console_output": "", + + "compute:reset_network": "", + "compute:inject_network_info": "", + "compute:add_fixed_ip": "", + "compute:remove_fixed_ip": "", + + "compute:attach_volume": "", + "compute:detach_volume": "", + "compute:swap_volume": "", + + "compute:attach_interface": "", + "compute:detach_interface": "", + + "compute:set_admin_password": "", + + "compute:rescue": "", + "compute:unrescue": "", + + "compute:suspend": "", + "compute:resume": "", + + "compute:pause": "", + "compute:unpause": "", + + "compute:shelve": "", + "compute:shelve_offload": "", + "compute:unshelve": "", + + "compute:snapshot": "", + "compute:snapshot_volume_backed": "", + "compute:backup": "", + + "compute:resize": "", + "compute:confirm_resize": "", + "compute:revert_resize": "", + + "compute:rebuild": "", + "compute:reboot": "", + "compute:delete": "rule:admin_or_owner", + "compute:soft_delete": "rule:admin_or_owner", + "compute:force_delete": "rule:admin_or_owner", + + "compute:security_groups:add_to_instance": "", + "compute:security_groups:remove_from_instance": "", + + "compute:delete": "", + "compute:soft_delete": "", + "compute:force_delete": "", + "compute:restore": "", + + "compute:volume_snapshot_create": "", + "compute:volume_snapshot_delete": "", + + "admin_api": "is_admin:True", + "compute_extension:accounts": "rule:admin_api", + "compute_extension:admin_actions": "rule:admin_api", + "compute_extension:admin_actions:pause": "rule:admin_or_owner", + "compute_extension:admin_actions:unpause": "rule:admin_or_owner", + "compute_extension:admin_actions:suspend": "rule:admin_or_owner", + "compute_extension:admin_actions:resume": "rule:admin_or_owner", + "compute_extension:admin_actions:lock": "rule:admin_or_owner", + "compute_extension:admin_actions:unlock": "rule:admin_or_owner", + "compute_extension:admin_actions:resetNetwork": "rule:admin_api", + "compute_extension:admin_actions:injectNetworkInfo": "rule:admin_api", + "compute_extension:admin_actions:createBackup": "rule:admin_or_owner", + "compute_extension:admin_actions:migrateLive": "rule:admin_api", + "compute_extension:admin_actions:resetState": "rule:admin_api", + "compute_extension:admin_actions:migrate": "rule:admin_api", + "compute_extension:aggregates": "rule:admin_api", + "compute_extension:agents": "rule:admin_api", + "compute_extension:attach_interfaces": "", + "compute_extension:baremetal_nodes": "rule:admin_api", + "compute_extension:cells": "rule:admin_api", + "compute_extension:cells:create": "rule:admin_api", + "compute_extension:cells:delete": "rule:admin_api", + "compute_extension:cells:update": "rule:admin_api", + "compute_extension:cells:sync_instances": "rule:admin_api", + "compute_extension:certificates": "", + "compute_extension:cloudpipe": "rule:admin_api", + "compute_extension:cloudpipe_update": "rule:admin_api", + "compute_extension:config_drive": "", + "compute_extension:console_output": "", + "compute_extension:consoles": "", + "compute_extension:createserverext": "", + "compute_extension:deferred_delete": "", + "compute_extension:disk_config": "", + "compute_extension:evacuate": "rule:admin_api", + "compute_extension:extended_server_attributes": "rule:admin_api", + "compute_extension:extended_status": "", + "compute_extension:extended_availability_zone": "", + "compute_extension:extended_ips": "", + "compute_extension:extended_ips_mac": "", + "compute_extension:extended_vif_net": "", + "compute_extension:extended_volumes": "", + "compute_extension:fixed_ips": "rule:admin_api", + "compute_extension:flavor_access": "", + "compute_extension:flavor_access:addTenantAccess": "rule:admin_api", + "compute_extension:flavor_access:removeTenantAccess": "rule:admin_api", + "compute_extension:flavor_disabled": "", + "compute_extension:flavor_rxtx": "", + "compute_extension:flavor_swap": "", + "compute_extension:flavorextradata": "", + "compute_extension:flavorextraspecs:index": "", + "compute_extension:flavorextraspecs:show": "", + "compute_extension:flavorextraspecs:create": "rule:admin_api", + "compute_extension:flavorextraspecs:update": "rule:admin_api", + "compute_extension:flavorextraspecs:delete": "rule:admin_api", + "compute_extension:flavormanage": "rule:admin_api", + "compute_extension:floating_ip_dns": "", + "compute_extension:floating_ip_pools": "", + "compute_extension:floating_ips": "", + "compute_extension:floating_ips_bulk": "rule:admin_api", + "compute_extension:fping": "", + "compute_extension:fping:all_tenants": "rule:admin_api", + "compute_extension:hide_server_addresses": "is_admin:False", + "compute_extension:hosts": "rule:admin_api", + "compute_extension:hypervisors": "rule:admin_api", + "compute_extension:image_size": "", + "compute_extension:instance_actions": "", + "compute_extension:instance_actions:events": "rule:admin_api", + "compute_extension:instance_usage_audit_log": "rule:admin_api", + "compute_extension:keypairs": "", + "compute_extension:keypairs:index": "", + "compute_extension:keypairs:show": "", + "compute_extension:keypairs:create": "", + "compute_extension:keypairs:delete": "", + "compute_extension:multinic": "", + "compute_extension:networks": "rule:admin_api", + "compute_extension:networks:view": "", + "compute_extension:networks_associate": "rule:admin_api", + "compute_extension:os-tenant-networks": "", + "compute_extension:quotas:show": "", + "compute_extension:quotas:update": "rule:admin_api", + "compute_extension:quotas:delete": "rule:admin_api", + "compute_extension:quota_classes": "", + "compute_extension:rescue": "", + "compute_extension:security_group_default_rules": "rule:admin_api", + "compute_extension:security_groups": "", + "compute_extension:server_diagnostics": "rule:admin_api", + "compute_extension:server_groups": "", + "compute_extension:server_password": "", + "compute_extension:server_usage": "", + "compute_extension:services": "rule:admin_api", + "compute_extension:shelve": "", + "compute_extension:shelveOffload": "rule:admin_api", + "compute_extension:simple_tenant_usage:show": "rule:admin_or_owner", + "compute_extension:simple_tenant_usage:list": "rule:admin_api", + "compute_extension:unshelve": "", + "compute_extension:users": "rule:admin_api", + "compute_extension:virtual_interfaces": "", + "compute_extension:virtual_storage_arrays": "", + "compute_extension:volumes": "", + "compute_extension:volume_attachments:index": "", + "compute_extension:volume_attachments:show": "", + "compute_extension:volume_attachments:create": "", + "compute_extension:volume_attachments:update": "", + "compute_extension:volume_attachments:delete": "", + "compute_extension:volumetypes": "", + "compute_extension:availability_zone:list": "", + "compute_extension:availability_zone:detail": "rule:admin_api", + "compute_extension:used_limits_for_admin": "rule:admin_api", + "compute_extension:migrations:index": "rule:admin_api", + "compute_extension:os-assisted-volume-snapshots:create": "rule:admin_api", + "compute_extension:os-assisted-volume-snapshots:delete": "rule:admin_api", + "compute_extension:console_auth_tokens": "rule:admin_api", + "compute_extension:os-server-external-events:create": "rule:admin_api", + + "network:get_all": "", + "network:get": "", + "network:create": "", + "network:delete": "", + "network:associate": "", + "network:disassociate": "", + "network:get_vifs_by_instance": "", + "network:allocate_for_instance": "", + "network:deallocate_for_instance": "", + "network:validate_networks": "", + "network:get_instance_uuids_by_ip_filter": "", + "network:get_instance_id_by_floating_address": "", + "network:setup_networks_on_host": "", + "network:get_backdoor_port": "", + + "network:get_floating_ip": "", + "network:get_floating_ip_pools": "", + "network:get_floating_ip_by_address": "", + "network:get_floating_ips_by_project": "", + "network:get_floating_ips_by_fixed_address": "", + "network:allocate_floating_ip": "", + "network:associate_floating_ip": "", + "network:disassociate_floating_ip": "", + "network:release_floating_ip": "", + "network:migrate_instance_start": "", + "network:migrate_instance_finish": "", + + "network:get_fixed_ip": "", + "network:get_fixed_ip_by_address": "", + "network:add_fixed_ip_to_instance": "", + "network:remove_fixed_ip_from_instance": "", + "network:add_network_to_project": "", + "network:get_instance_nw_info": "", + + "network:get_dns_domains": "", + "network:add_dns_entry": "", + "network:modify_dns_entry": "", + "network:delete_dns_entry": "", + "network:get_dns_entries_by_address": "", + "network:get_dns_entries_by_name": "", + "network:create_private_dns_domain": "", + "network:create_public_dns_domain": "", + "network:delete_dns_domain": "", + "network:attach_external_network": "rule:admin_api", + "network:get_vif_by_mac_address": "", + + "os_compute_api:servers:detail:get_all_tenants": "is_admin:True", + "os_compute_api:servers:index:get_all_tenants": "is_admin:True", + "os_compute_api:servers:confirm_resize": "", + "os_compute_api:servers:create": "http://my_hostname:31001/authz", + "os_compute_api:servers:create:attach_network": "", + "os_compute_api:servers:create:attach_volume": "", + "os_compute_api:servers:create:forced_host": "rule:admin_api", + "os_compute_api:servers:delete": "http://my_hostname:31001/authz", + "os_compute_api:servers:update": "http://my_hostname:31001/authz", + "os_compute_api:servers:detail": "http://my_hostname:31001/authz", + "os_compute_api:servers:index": "http://my_hostname:31001/authz", + "os_compute_api:servers:reboot": "http://my_hostname:31001/authz", + "os_compute_api:servers:rebuild": "http://my_hostname:31001/authz", + "os_compute_api:servers:resize": "http://my_hostname:31001/authz", + "os_compute_api:servers:revert_resize": "http://my_hostname:31001/authz", + "os_compute_api:servers:show": "http://my_hostname:31001/authz", + "os_compute_api:servers:create_image": "", + "os_compute_api:servers:create_image:allow_volume_backed": "", + "os_compute_api:servers:start": "rule:admin_or_owner", + "os_compute_api:servers:stop": "rule:admin_or_owner", + "os_compute_api:os-access-ips:discoverable": "", + "os_compute_api:os-access-ips": "", + "os_compute_api:os-admin-actions": "rule:admin_api", + "os_compute_api:os-admin-actions:discoverable": "", + "os_compute_api:os-admin-actions:reset_network": "rule:admin_api", + "os_compute_api:os-admin-actions:inject_network_info": "rule:admin_api", + "os_compute_api:os-admin-actions:reset_state": "rule:admin_api", + "os_compute_api:os-admin-password": "", + "os_compute_api:os-admin-password:discoverable": "", + "os_compute_api:os-aggregates:discoverable": "", + "os_compute_api:os-aggregates:index": "rule:admin_api", + "os_compute_api:os-aggregates:create": "rule:admin_api", + "os_compute_api:os-aggregates:show": "rule:admin_api", + "os_compute_api:os-aggregates:update": "rule:admin_api", + "os_compute_api:os-aggregates:delete": "rule:admin_api", + "os_compute_api:os-aggregates:add_host": "rule:admin_api", + "os_compute_api:os-aggregates:remove_host": "rule:admin_api", + "os_compute_api:os-aggregates:set_metadata": "rule:admin_api", + "os_compute_api:os-agents": "rule:admin_api", + "os_compute_api:os-agents:discoverable": "", + "os_compute_api:os-attach-interfaces": "", + "os_compute_api:os-attach-interfaces:discoverable": "", + "os_compute_api:os-baremetal-nodes": "rule:admin_api", + "os_compute_api:os-baremetal-nodes:discoverable": "", + "os_compute_api:os-block-device-mapping-v1:discoverable": "", + "os_compute_api:os-cells": "rule:admin_api", + "os_compute_api:os-cells:create": "rule:admin_api", + "os_compute_api:os-cells:delete": "rule:admin_api", + "os_compute_api:os-cells:update": "rule:admin_api", + "os_compute_api:os-cells:sync_instances": "rule:admin_api", + "os_compute_api:os-cells:discoverable": "", + "os_compute_api:os-certificates:create": "", + "os_compute_api:os-certificates:show": "", + "os_compute_api:os-certificates:discoverable": "", + "os_compute_api:os-cloudpipe": "rule:admin_api", + "os_compute_api:os-cloudpipe:discoverable": "", + "os_compute_api:os-config-drive": "", + "os_compute_api:os-consoles:discoverable": "", + "os_compute_api:os-consoles:create": "", + "os_compute_api:os-consoles:delete": "", + "os_compute_api:os-consoles:index": "", + "os_compute_api:os-consoles:show": "", + "os_compute_api:os-console-output:discoverable": "", + "os_compute_api:os-console-output": "", + "os_compute_api:os-remote-consoles": "", + "os_compute_api:os-remote-consoles:discoverable": "", + "os_compute_api:os-create-backup:discoverable": "", + "os_compute_api:os-create-backup": "rule:admin_or_owner", + "os_compute_api:os-deferred-delete": "", + "os_compute_api:os-deferred-delete:discoverable": "", + "os_compute_api:os-disk-config": "", + "os_compute_api:os-disk-config:discoverable": "", + "os_compute_api:os-evacuate": "rule:admin_api", + "os_compute_api:os-evacuate:discoverable": "", + "os_compute_api:os-extended-server-attributes": "rule:admin_api", + "os_compute_api:os-extended-server-attributes:discoverable": "", + "os_compute_api:os-extended-status": "", + "os_compute_api:os-extended-status:discoverable": "", + "os_compute_api:os-extended-availability-zone": "", + "os_compute_api:os-extended-availability-zone:discoverable": "", + "os_compute_api:extensions": "", + "os_compute_api:extension_info:discoverable": "", + "os_compute_api:os-extended-volumes": "", + "os_compute_api:os-extended-volumes:discoverable": "", + "os_compute_api:os-fixed-ips": "rule:admin_api", + "os_compute_api:os-fixed-ips:discoverable": "", + "os_compute_api:os-flavor-access": "", + "os_compute_api:os-flavor-access:discoverable": "", + "os_compute_api:os-flavor-access:remove_tenant_access": "rule:admin_api", + "os_compute_api:os-flavor-access:add_tenant_access": "rule:admin_api", + "os_compute_api:os-flavor-rxtx": "", + "os_compute_api:os-flavor-rxtx:discoverable": "", + "os_compute_api:flavors:discoverable": "", + "os_compute_api:os-flavor-extra-specs:discoverable": "", + "os_compute_api:os-flavor-extra-specs:index": "", + "os_compute_api:os-flavor-extra-specs:show": "", + "os_compute_api:os-flavor-extra-specs:create": "rule:admin_api", + "os_compute_api:os-flavor-extra-specs:update": "rule:admin_api", + "os_compute_api:os-flavor-extra-specs:delete": "rule:admin_api", + "os_compute_api:os-flavor-manage:discoverable": "", + "os_compute_api:os-flavor-manage": "rule:admin_api", + "os_compute_api:os-floating-ip-dns": "", + "os_compute_api:os-floating-ip-dns:discoverable": "", + "os_compute_api:os-floating-ip-dns:domain:update": "rule:admin_api", + "os_compute_api:os-floating-ip-dns:domain:delete": "rule:admin_api", + "os_compute_api:os-floating-ip-pools": "", + "os_compute_api:os-floating-ip-pools:discoverable": "", + "os_compute_api:os-floating-ips": "", + "os_compute_api:os-floating-ips:discoverable": "", + "os_compute_api:os-floating-ips-bulk": "rule:admin_api", + "os_compute_api:os-floating-ips-bulk:discoverable": "", + "os_compute_api:os-fping": "", + "os_compute_api:os-fping:discoverable": "", + "os_compute_api:os-fping:all_tenants": "rule:admin_api", + "os_compute_api:os-hide-server-addresses": "is_admin:False", + "os_compute_api:os-hide-server-addresses:discoverable": "", + "os_compute_api:os-hosts": "rule:admin_api", + "os_compute_api:os-hosts:discoverable": "", + "os_compute_api:os-hypervisors": "rule:admin_api", + "os_compute_api:os-hypervisors:discoverable": "", + "os_compute_api:images:discoverable": "", + "os_compute_api:image-size": "", + "os_compute_api:image-size:discoverable": "", + "os_compute_api:os-instance-actions": "", + "os_compute_api:os-instance-actions:discoverable": "", + "os_compute_api:os-instance-actions:events": "rule:admin_api", + "os_compute_api:os-instance-usage-audit-log": "rule:admin_api", + "os_compute_api:os-instance-usage-audit-log:discoverable": "", + "os_compute_api:ips:discoverable": "", + "os_compute_api:ips:index": "rule:admin_or_owner", + "os_compute_api:ips:show": "rule:admin_or_owner", + "os_compute_api:os-keypairs:discoverable": "", + "os_compute_api:os-keypairs": "", + "os_compute_api:os-keypairs:index": "rule:admin_api or user_id:%(user_id)s", + "os_compute_api:os-keypairs:show": "rule:admin_api or user_id:%(user_id)s", + "os_compute_api:os-keypairs:create": "rule:admin_api or user_id:%(user_id)s", + "os_compute_api:os-keypairs:delete": "rule:admin_api or user_id:%(user_id)s", + "os_compute_api:limits:discoverable": "", + "os_compute_api:limits": "", + "os_compute_api:os-lock-server:discoverable": "", + "os_compute_api:os-lock-server:lock": "rule:admin_or_owner", + "os_compute_api:os-lock-server:unlock": "rule:admin_or_owner", + "os_compute_api:os-lock-server:unlock:unlock_override": "rule:admin_api", + "os_compute_api:os-migrate-server:discoverable": "", + "os_compute_api:os-migrate-server:migrate": "rule:admin_api", + "os_compute_api:os-migrate-server:migrate_live": "rule:admin_api", + "os_compute_api:os-multinic": "", + "os_compute_api:os-multinic:discoverable": "", + "os_compute_api:os-networks": "rule:admin_api", + "os_compute_api:os-networks:view": "", + "os_compute_api:os-networks:discoverable": "", + "os_compute_api:os-networks-associate": "rule:admin_api", + "os_compute_api:os-networks-associate:discoverable": "", + "os_compute_api:os-pause-server:discoverable": "", + "os_compute_api:os-pause-server:pause": "rule:admin_or_owner", + "os_compute_api:os-pause-server:unpause": "rule:admin_or_owner", + "os_compute_api:os-pci:pci_servers": "", + "os_compute_api:os-pci:discoverable": "", + "os_compute_api:os-pci:index": "rule:admin_api", + "os_compute_api:os-pci:detail": "rule:admin_api", + "os_compute_api:os-pci:show": "rule:admin_api", + "os_compute_api:os-personality:discoverable": "", + "os_compute_api:os-preserve-ephemeral-rebuild:discoverable": "", + "os_compute_api:os-quota-sets:discoverable": "", + "os_compute_api:os-quota-sets:show": "rule:admin_or_owner", + "os_compute_api:os-quota-sets:defaults": "", + "os_compute_api:os-quota-sets:update": "rule:admin_api", + "os_compute_api:os-quota-sets:delete": "rule:admin_api", + "os_compute_api:os-quota-sets:detail": "rule:admin_api", + "os_compute_api:os-quota-class-sets:update": "rule:admin_api", + "os_compute_api:os-quota-class-sets:show": "is_admin:True or quota_class:%(quota_class)s", + "os_compute_api:os-quota-class-sets:discoverable": "", + "os_compute_api:os-rescue": "", + "os_compute_api:os-rescue:discoverable": "", + "os_compute_api:os-scheduler-hints:discoverable": "", + "os_compute_api:os-security-group-default-rules:discoverable": "", + "os_compute_api:os-security-group-default-rules": "rule:admin_api", + "os_compute_api:os-security-groups": "", + "os_compute_api:os-security-groups:discoverable": "", + "os_compute_api:os-server-diagnostics": "rule:admin_api", + "os_compute_api:os-server-diagnostics:discoverable": "", + "os_compute_api:os-server-password": "", + "os_compute_api:os-server-password:discoverable": "", + "os_compute_api:os-server-usage": "", + "os_compute_api:os-server-usage:discoverable": "", + "os_compute_api:os-server-groups": "", + "os_compute_api:os-server-groups:discoverable": "", + "os_compute_api:os-services": "rule:admin_api", + "os_compute_api:os-services:discoverable": "", + "os_compute_api:server-metadata:discoverable": "", + "os_compute_api:server-metadata:index": "rule:admin_or_owner", + "os_compute_api:server-metadata:show": "rule:admin_or_owner", + "os_compute_api:server-metadata:delete": "rule:admin_or_owner", + "os_compute_api:server-metadata:create": "rule:admin_or_owner", + "os_compute_api:server-metadata:update": "rule:admin_or_owner", + "os_compute_api:server-metadata:update_all": "rule:admin_or_owner", + "os_compute_api:servers:discoverable": "", + "os_compute_api:os-shelve:shelve": "", + "os_compute_api:os-shelve:shelve:discoverable": "", + "os_compute_api:os-shelve:shelve_offload": "rule:admin_api", + "os_compute_api:os-simple-tenant-usage:discoverable": "", + "os_compute_api:os-simple-tenant-usage:show": "rule:admin_or_owner", + "os_compute_api:os-simple-tenant-usage:list": "rule:admin_api", + "os_compute_api:os-suspend-server:discoverable": "", + "os_compute_api:os-suspend-server:suspend": "rule:admin_or_owner", + "os_compute_api:os-suspend-server:resume": "rule:admin_or_owner", + "os_compute_api:os-tenant-networks": "rule:admin_or_owner", + "os_compute_api:os-tenant-networks:discoverable": "", + "os_compute_api:os-shelve:unshelve": "", + "os_compute_api:os-user-data:discoverable": "", + "os_compute_api:os-virtual-interfaces": "", + "os_compute_api:os-virtual-interfaces:discoverable": "", + "os_compute_api:os-volumes": "", + "os_compute_api:os-volumes:discoverable": "", + "os_compute_api:os-volumes-attachments:index": "", + "os_compute_api:os-volumes-attachments:show": "", + "os_compute_api:os-volumes-attachments:create": "", + "os_compute_api:os-volumes-attachments:update": "", + "os_compute_api:os-volumes-attachments:delete": "", + "os_compute_api:os-volumes-attachments:discoverable": "", + "os_compute_api:os-availability-zone:list": "", + "os_compute_api:os-availability-zone:discoverable": "", + "os_compute_api:os-availability-zone:detail": "rule:admin_api", + "os_compute_api:os-used-limits": "rule:admin_api", + "os_compute_api:os-used-limits:discoverable": "", + "os_compute_api:os-migrations:index": "rule:admin_api", + "os_compute_api:os-migrations:discoverable": "", + "os_compute_api:os-assisted-volume-snapshots:create": "rule:admin_api", + "os_compute_api:os-assisted-volume-snapshots:delete": "rule:admin_api", + "os_compute_api:os-assisted-volume-snapshots:discoverable": "", + "os_compute_api:os-console-auth-tokens": "rule:admin_api", + "os_compute_api:os-server-external-events:create": "rule:admin_api" +} diff --git a/templates/python_unit_test/Dockerfile b/templates/python_unit_test/Dockerfile new file mode 100644 index 00000000..b8fb5151 --- /dev/null +++ b/templates/python_unit_test/Dockerfile @@ -0,0 +1,8 @@ +FROM python:3 + +RUN pip install pytest requests_mock requests --upgrade +ADD requirements.txt /root +RUN pip install -r /root/requirements.txt --upgrade + +ADD run_tests.sh /root +CMD ["sh", "/root/run_tests.sh"] \ No newline at end of file diff --git a/templates/python_unit_test/README.md b/templates/python_unit_test/README.md new file mode 100644 index 00000000..45d3a988 --- /dev/null +++ b/templates/python_unit_test/README.md @@ -0,0 +1,8 @@ +# Python Unit Test Docker + +## Build +- `docker image build -t wukongsun/moon_python_unit_test .` + +## Push to DockerHub +- `docker login --username=wukongsun` +- `docker image push wukongsun/moon_python_unit_test` \ No newline at end of file diff --git a/templates/python_unit_test/requirements.txt b/templates/python_unit_test/requirements.txt new file mode 100644 index 00000000..b611b008 --- /dev/null +++ b/templates/python_unit_test/requirements.txt @@ -0,0 +1,10 @@ +kombu !=4.0.1,!=4.0.0 +oslo.messaging +oslo.config +oslo.log +vine +werkzeug +flask +requests +pytest +requests_mock \ No newline at end of file diff --git a/templates/python_unit_test/run_tests.sh b/templates/python_unit_test/run_tests.sh new file mode 100644 index 00000000..6c586f87 --- /dev/null +++ b/templates/python_unit_test/run_tests.sh @@ -0,0 +1,13 @@ +#!/usr/bin/env bash + +cd /data +pip3 install -r tests/unit_python/requirements.txt --upgrade +pip3 install . + +if [ -f /data/tests/unit_python/run_tests.sh ]; +then + bash /data/tests/unit_python/run_tests.sh; +fi + +cd /data/tests/unit_python +pytest . -- cgit 1.2.3-korg