def post(self, rule, requester_user): """ Create a new rule. Handles requests: POST /rules/ """ permission_type = PermissionType.RULE_CREATE rbac_utils.assert_user_has_resource_api_permission(user_db=requester_user, resource_api=rule, permission_type=permission_type) if not requester_user: requester_user = UserDB(cfg.CONF.system_user.user) # Validate that the authenticated user is admin if user query param is provided user = requester_user.name assert_user_is_admin_if_user_query_param_is_provided(user_db=requester_user, user=user) if not hasattr(rule, 'context'): rule.context = dict() rule.context['user'] = user try: rule_db = RuleAPI.to_model(rule) LOG.debug('/rules/ POST verified RuleAPI and formulated RuleDB=%s', rule_db) # Check referenced trigger and action permissions # Note: This needs to happen after "to_model" call since to_model performs some # validation (trigger exists, etc.) assert_user_has_rule_trigger_and_action_permission(user_db=requester_user, rule_api=rule) rule_db = Rule.add_or_update(rule_db) # After the rule has been added modify the ref_count. This way a failure to add # the rule due to violated constraints will have no impact on ref_count. increment_trigger_ref_count(rule_api=rule) except (ValidationError, ValueError) as e: LOG.exception('Validation failed for rule data=%s.', rule) abort(http_client.BAD_REQUEST, str(e)) return except (ValueValidationException, jsonschema.ValidationError) as e: LOG.exception('Validation failed for rule data=%s.', rule) abort(http_client.BAD_REQUEST, str(e)) return except TriggerDoesNotExistException as e: msg = ('Trigger "%s" defined in the rule does not exist in system or it\'s missing ' 'required "parameters" attribute' % (rule.trigger['type'])) LOG.exception(msg) abort(http_client.BAD_REQUEST, msg) return extra = {'rule_db': rule_db} LOG.audit('Rule created. Rule.id=%s' % (rule_db.id), extra=extra) rule_api = RuleAPI.from_model(rule_db) return Response(json=rule_api, status=exc.HTTPCreated.code)
def post(self, instance, requester_user): """ Create a new policy. Handles requests: POST /policies/ """ permission_type = PermissionType.POLICY_CREATE rbac_utils.assert_user_has_resource_api_permission( user_db=requester_user, resource_api=instance, permission_type=permission_type) op = 'POST /policies/' db_model = self.model.to_model(instance) LOG.debug('%s verified object: %s', op, db_model) db_model = self.access.add_or_update(db_model) LOG.debug('%s created object: %s', op, db_model) LOG.audit('Policy created. Policy.id=%s' % (db_model.id), extra={'policy_db': db_model}) exec_result = self.model.from_model(db_model) return Response(json=exec_result, status=http_client.CREATED)
def post(self, action_alias, requester_user): """ Create a new ActionAlias. Handles requests: POST /actionalias/ """ permission_type = PermissionType.ACTION_ALIAS_CREATE rbac_utils.assert_user_has_resource_api_permission( user_db=requester_user, resource_api=action_alias, permission_type=permission_type) try: action_alias_db = ActionAliasAPI.to_model(action_alias) LOG.debug( '/actionalias/ POST verified ActionAliasAPI and formulated ActionAliasDB=%s', action_alias_db) action_alias_db = ActionAlias.add_or_update(action_alias_db) except (ValidationError, ValueError, ValueValidationException) as e: LOG.exception('Validation failed for action alias data=%s.', action_alias) abort(http_client.BAD_REQUEST, str(e)) return extra = {'action_alias_db': action_alias_db} LOG.audit('Action alias created. ActionAlias.id=%s' % (action_alias_db.id), extra=extra) action_alias_api = ActionAliasAPI.from_model(action_alias_db) return Response(json=action_alias_api, status=http_client.CREATED)
def post(self, rule, requester_user): """ Create a new rule. Handles requests: POST /rules/ """ permission_type = PermissionType.RULE_CREATE rbac_utils.assert_user_has_resource_api_permission(user_db=requester_user, resource_api=rule, permission_type=permission_type) if not requester_user: requester_user = UserDB(cfg.CONF.system_user.user) # Validate that the authenticated user is admin if user query param is provided user = requester_user.name assert_user_is_admin_if_user_query_param_is_provided(user_db=requester_user, user=user) if not hasattr(rule, 'context'): rule.context = dict() rule.context['user'] = user try: rule_db = RuleAPI.to_model(rule) LOG.debug('/rules/ POST verified RuleAPI and formulated RuleDB=%s', rule_db) # Check referenced trigger and action permissions # Note: This needs to happen after "to_model" call since to_model performs some # validation (trigger exists, etc.) assert_user_has_rule_trigger_and_action_permission(user_db=requester_user, rule_api=rule) rule_db = Rule.add_or_update(rule_db) # After the rule has been added modify the ref_count. This way a failure to add # the rule due to violated constraints will have no impact on ref_count. increment_trigger_ref_count(rule_api=rule) except (ValidationError, ValueError) as e: LOG.exception('Validation failed for rule data=%s.', rule) abort(http_client.BAD_REQUEST, six.text_type(e)) return except (ValueValidationException, jsonschema.ValidationError) as e: LOG.exception('Validation failed for rule data=%s.', rule) abort(http_client.BAD_REQUEST, six.text_type(e)) return except TriggerDoesNotExistException as e: msg = ('Trigger "%s" defined in the rule does not exist in system or it\'s missing ' 'required "parameters" attribute' % (rule.trigger['type'])) LOG.exception(msg) abort(http_client.BAD_REQUEST, msg) return extra = {'rule_db': rule_db} LOG.audit('Rule created. Rule.id=%s' % (rule_db.id), extra=extra) rule_api = RuleAPI.from_model(rule_db) return Response(json=rule_api, status=exc.HTTPCreated.code)
def post(self, action_alias, requester_user): """ Create a new ActionAlias. Handles requests: POST /actionalias/ """ permission_type = PermissionType.ACTION_ALIAS_CREATE rbac_utils.assert_user_has_resource_api_permission(user_db=requester_user, resource_api=action_alias, permission_type=permission_type) try: action_alias_db = ActionAliasAPI.to_model(action_alias) LOG.debug('/actionalias/ POST verified ActionAliasAPI and formulated ActionAliasDB=%s', action_alias_db) action_alias_db = ActionAlias.add_or_update(action_alias_db) except (ValidationError, ValueError, ValueValidationException) as e: LOG.exception('Validation failed for action alias data=%s.', action_alias) abort(http_client.BAD_REQUEST, six.text_type(e)) return extra = {'action_alias_db': action_alias_db} LOG.audit('Action alias created. ActionAlias.id=%s' % (action_alias_db.id), extra=extra) action_alias_api = ActionAliasAPI.from_model(action_alias_db) return Response(json=action_alias_api, status=http_client.CREATED)
def post(self, api_key_api, requester_user): """ Create a new entry. """ permission_type = PermissionType.API_KEY_CREATE rbac_utils.assert_user_has_resource_api_permission( user_db=requester_user, resource_api=api_key_api, permission_type=permission_type) api_key_db = None api_key = None try: if not getattr(api_key_api, 'user', None): if requester_user: api_key_api.user = requester_user.name else: api_key_api.user = cfg.CONF.system_user.user try: User.get_by_name(api_key_api.user) except StackStormDBObjectNotFoundError: user_db = UserDB(name=api_key_api.user) User.add_or_update(user_db) extra = {'username': api_key_api.user, 'user': user_db} LOG.audit('Registered new user "%s".' % (api_key_api.user), extra=extra) # If key_hash is provided use that and do not create a new key. The assumption # is user already has the original api-key if not getattr(api_key_api, 'key_hash', None): api_key, api_key_hash = auth_util.generate_api_key_and_hash() # store key_hash in DB api_key_api.key_hash = api_key_hash api_key_db = ApiKey.add_or_update(ApiKeyAPI.to_model(api_key_api)) except (ValidationError, ValueError) as e: LOG.exception('Validation failed for api_key data=%s.', api_key_api) abort(http_client.BAD_REQUEST, six.text_type(e)) extra = {'api_key_db': api_key_db} LOG.audit('ApiKey created. ApiKey.id=%s' % (api_key_db.id), extra=extra) api_key_create_response_api = ApiKeyCreateResponseAPI.from_model( api_key_db) # Return real api_key back to user. A one-way hash of the api_key is stored in the DB # only the real value only returned at create time. Also, no masking of key here since # the user needs to see this value atleast once. api_key_create_response_api.key = api_key return Response(json=api_key_create_response_api, status=http_client.CREATED)
def post(self, api_key_api, requester_user): """ Create a new entry. """ permission_type = PermissionType.API_KEY_CREATE rbac_utils.assert_user_has_resource_api_permission(user_db=requester_user, resource_api=api_key_api, permission_type=permission_type) api_key_db = None api_key = None try: if not getattr(api_key_api, 'user', None): if requester_user: api_key_api.user = requester_user.name else: api_key_api.user = cfg.CONF.system_user.user try: User.get_by_name(api_key_api.user) except StackStormDBObjectNotFoundError: user_db = UserDB(name=api_key_api.user) User.add_or_update(user_db) extra = {'username': api_key_api.user, 'user': user_db} LOG.audit('Registered new user "%s".' % (api_key_api.user), extra=extra) # If key_hash is provided use that and do not create a new key. The assumption # is user already has the original api-key if not getattr(api_key_api, 'key_hash', None): api_key, api_key_hash = auth_util.generate_api_key_and_hash() # store key_hash in DB api_key_api.key_hash = api_key_hash api_key_db = ApiKey.add_or_update(ApiKeyAPI.to_model(api_key_api)) except (ValidationError, ValueError) as e: LOG.exception('Validation failed for api_key data=%s.', api_key_api) abort(http_client.BAD_REQUEST, six.text_type(e)) extra = {'api_key_db': api_key_db} LOG.audit('ApiKey created. ApiKey.id=%s' % (api_key_db.id), extra=extra) api_key_create_response_api = ApiKeyCreateResponseAPI.from_model(api_key_db) # Return real api_key back to user. A one-way hash of the api_key is stored in the DB # only the real value only returned at create time. Also, no masking of key here since # the user needs to see this value atleast once. api_key_create_response_api.key = api_key return Response(json=api_key_create_response_api, status=http_client.CREATED)
def post(self, action, requester_user): """ Create a new action. Handles requests: POST /actions/ """ permission_type = PermissionType.ACTION_CREATE rbac_utils.assert_user_has_resource_api_permission( user_db=requester_user, resource_api=action, permission_type=permission_type) try: # Perform validation validate_not_part_of_system_pack(action) action_validator.validate_action(action) except (ValidationError, ValueError, ValueValidationException, InvalidActionParameterException) as e: LOG.exception('Unable to create action data=%s', action) abort(http_client.BAD_REQUEST, str(e)) return # Write pack data files to disk (if any are provided) data_files = getattr(action, 'data_files', []) written_data_files = [] if data_files: written_data_files = self._handle_data_files(pack_ref=action.pack, data_files=data_files) action_model = ActionAPI.to_model(action) LOG.debug('/actions/ POST verified ActionAPI object=%s', action) action_db = Action.add_or_update(action_model) LOG.debug('/actions/ POST saved ActionDB object=%s', action_db) # Dispatch an internal trigger for each written data file. This way user # automate comitting this files to git using StackStorm rule if written_data_files: self._dispatch_trigger_for_written_data_files( action_db=action_db, written_data_files=written_data_files) extra = {'acion_db': action_db} LOG.audit('Action created. Action.id=%s' % (action_db.id), extra=extra) action_api = ActionAPI.from_model(action_db) return Response(json=action_api, status=http_client.CREATED)
def post(self, instance, requester_user): """ Create a new policy. Handles requests: POST /policies/ """ permission_type = PermissionType.POLICY_CREATE rbac_utils.assert_user_has_resource_api_permission(user_db=requester_user, resource_api=instance, permission_type=permission_type) op = 'POST /policies/' db_model = self.model.to_model(instance) LOG.debug('%s verified object: %s', op, db_model) db_model = self.access.add_or_update(db_model) LOG.debug('%s created object: %s', op, db_model) LOG.audit('Policy created. Policy.id=%s' % (db_model.id), extra={'policy_db': db_model}) exec_result = self.model.from_model(db_model) return Response(json=exec_result, status=http_client.CREATED)