def apply(self, xmlgpo): result = True converted = self.convert(xmlgpo) if converted is None: # TODO: Inform about the problem return False for entry in converted: if result is False: break for guid in entry['guids']: if result is False: break node = self.collection.find_one({'adObjectGUID': guid}) domain = get_domain(node, self.collection) if node is None: result = False # TODO: Inform about the problem continue old_node = deepcopy(node) for policy in entry['policies']: policy_id = policy.keys()[0] if policy_id not in domain.get('master_policies', {}) and node.get('policies', {}).get(policy_id, None): continue node['policies'][policy_id] = policy[policy_id] result = self._saveMongoADObject(node, old_node) return result
def is_gecos_master_or_403(request, collection_nodes, obj, schema_detail): domain = get_domain(obj, collection_nodes) if domain and domain['master'] != MASTER_DEFAULT and not is_local_user(obj, collection_nodes): if '_id' not in obj: raise HTTPForbidden() else: mongo_obj = collection_nodes.find_one({'_id': ObjectId(obj['_id'])}) mongo_obj = schema_detail().serialize(mongo_obj) obj = schema_detail().serialize(obj) del obj['policies'] del mongo_obj['policies'] if obj != mongo_obj: raise HTTPForbidden()
def check_unique_node_name_by_type_at_domain(self, obj): unique = check_unique_node_name_by_type_at_domain( self.request.db.nodes, obj) if not unique: self.request.errors.add('body', 'name', "Name must be unique in domain.") if unique and not is_domain(obj) and not is_root(obj): # Check that the node name is not the same as the domain name domain = get_domain(obj, self.request.db.nodes) if domain['name'].lower() == obj['name'].lower(): self.request.errors.add('body', 'name', "Name already used as domain name.") return False return unique
def master_policy_no_updated_or_403(request, collection_nodes, obj): if obj['type'] in RESOURCES_EMITTERS_TYPES or is_local_user(obj, collection_nodes): return domain = get_domain(obj, collection_nodes) or {} master_policies = domain.get('master_policies', {}) if master_policies: if '_id' in obj: mongo_obj = collection_nodes.find_one({'_id': obj['_id']}) else: mongo_obj = {} mongo_policies = mongo_obj.get('policies', {}) policies = obj.get('policies', {}) for policy_id, value in master_policies.items(): if mongo_policies.get(policy_id, None) != policies.get(policy_id, None): raise HTTPForbidden()
def master_policy_no_updated_or_403(request, collection_nodes, obj): if obj['type'] in RESOURCES_EMITTERS_TYPES or is_local_user(obj, collection_nodes): return domain = get_domain(obj, collection_nodes) or {} master_policies = domain.get('master_policies', {}) if master_policies: if '_id' in obj: mongo_obj = collection_nodes.find_one({'_id': obj['_id']}) else: mongo_obj = {} mongo_policies = mongo_obj.get('policies', {}) policies = obj.get('policies', {}) for policy_id, _value in master_policies.items(): if mongo_policies.get(policy_id, None) != policies.get(policy_id, None): raise HTTPForbidden()
def check_node(self, node): ''' Check the policies applied to a node ''' logger.info('Checking node: "%s" type:%s path: %s' % (node['name'], node['type'], node['path'])) # Check for name duplicates if not check_unique_node_name_by_type_at_domain(self.db.nodes, node): logger.error('Duplicates found for node: "%s" type:%s path: %s' % (node['name'], node['type'], node['path'])) elif not is_domain(node) and not is_root(node): # Check that the node name is not the same as the domain name domain = get_domain(node, self.db.nodes) if domain['name'].lower() == node['name'].lower(): logger.error( 'The node has the same name as the domain: "%s" type:%s path: %s' % (node['name'], node['type'], node['path'])) if self.options.inheritance: inheritance_node = deepcopy(node) # Check policies if 'policies' in node: to_remove = [] # Check the policies data for policy in node['policies']: logger.debug('Checking policy with ID: %s' % (policy)) if not str(policy) in self.policiesdata: logger.warn( "Can't find %s policy data in the database! (probably deprecated)" % (policy)) to_remove.append(str(policy)) else: policydata = self.policiesdata[str(policy)] nodedata = node['policies'][str(policy)] # Emiters policies have a "name" field in the data # Non emiters policies have a "title" field in the data namefield = 'name' if not (namefield in policydata): namefield = 'title' if not ('name' in policydata): logger.critical( 'Policy with ID: %s doesn\'t have a name nor title!' % (str(policy))) continue logger.info('Checking node: "%s" Checking policy: "%s"' % (node['name'], policydata[namefield])) if 'DEPRECATED' in policydata[namefield]: logger.warning('Using deprecated policy: %s' % (policydata[namefield])) logger.debug('Node policy data: %s' % (json.dumps(node['policies'][str(policy)]))) is_emitter_policy = False emitter_policy_slug = None if "is_emitter_policy" in policydata: is_emitter_policy = policydata["is_emitter_policy"] emitter_policy_slug = policydata["slug"] # Check object self.check_object_property(policydata['schema'], nodedata, None, is_emitter_policy, emitter_policy_slug) if self.options.inheritance: # Check inheritance field trace_inheritance(logger, self.db, 'change', inheritance_node, deepcopy(policydata)) changed = False for policy in to_remove: logger.info("FIXED: Remove %s policy information" % (policy)) del node['policies'][str(policy)] changed = True if changed: self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'policies': node['policies'] }}) else: logger.debug('No policies in this node.') if self.options.inheritance and ( 'inheritance' in inheritance_node) and ( (not 'inheritance' in node) or (inheritance_node['inheritance'] != node['inheritance'])): # Save inheritance field logger.info('FIXED: updating inheritance field!') self.db.nodes.update( {'_id': ObjectId(node['_id'])}, {'$set': { 'inheritance': inheritance_node['inheritance'] }}) # Check referenced nodes if node['type'] == 'user': # Check computers new_id_list = self.check_referenced_nodes(node['computers'], ['computer'], 'computers') difference = set(node['computers']).difference(set(new_id_list)) if len(difference) > 0: logger.info('FIXED: remove %s references' % (difference)) self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'computers': new_id_list }}) # Check user data self.check_user_data(node) # Check memberof new_id_list = self.check_referenced_nodes(node['memberof'], ['group'], 'memberof') difference = set(node['memberof']).difference(set(new_id_list)) if len(difference) > 0: logger.info('FIXED: remove %s references' % (difference)) self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'memberof': new_id_list }}) if node['type'] == 'computer': # Check memberof new_id_list = self.check_referenced_nodes(node['memberof'], ['group'], 'memberof') difference = set(node['memberof']).difference(set(new_id_list)) if len(difference) > 0: logger.info('FIXED: remove %s references' % (difference)) self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'memberof': new_id_list }}) if node['type'] == 'group': # Check memberof new_id_list = self.check_referenced_nodes(node['memberof'], ['group'], 'memberof') difference = set(node['memberof']).difference(set(new_id_list)) if len(difference) > 0: logger.info('FIXED: remove %s references' % (difference)) self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'memberof': new_id_list }}) # Check members new_id_list = self.check_referenced_nodes( node['members'], ['user', 'computer', 'group'], 'members') difference = set(node['members']).difference(set(new_id_list)) if len(difference) > 0: logger.info('FIXED: remove %s references' % (difference)) self.db.nodes.update({'_id': ObjectId(node['_id'])}, {'$set': { 'members': new_id_list }})