def subentry_with_name(self, name): entry = self.lobj.search_s(self.dn, ldap.SCOPE_SUBTREE, '(associatedDomain=%s.%s)' % (utils.utf8(name), utils.utf8(self.qualified_domain))) if entry: return HostEntry(self, entry[0]) else: return None
def add_entry(self, name, address): if self.subentry_with_name(name): raise exception.FloatingIpDNSExists(name=name, domain=self.qualified_domain) entries = self.subentries_with_ip(address) if entries: # We already have an ldap entry for this IP, so we just # need to add the new name. existingdn = entries[0].dn self.lobj.modify_s(existingdn, [(ldap.MOD_ADD, 'associatedDomain', utils.utf8(self._qualify(name)))]) return self.subentry_with_name(name) else: # We need to create an entirely new entry. newdn = 'dc=%s,%s' % (name, self.dn) attrs = {'objectClass': ['domainrelatedobject', 'dnsdomain', 'domain', 'dcobject', 'top'], 'aRecord': [address], 'associatedDomain': [self._qualify(name)], 'dc': [name]} self.lobj.add_s(newdn, create_modlist(attrs)) return self.subentry_with_name(name)
def create_modlist(newattrs): modlist = [] for attrtype in newattrs.keys(): utf8_vals = [] for val in newattrs[attrtype]: utf8_vals.append(utils.utf8(val)) newattrs[attrtype] = utf8_vals modlist.append((attrtype, newattrs[attrtype])) return modlist
def subentries_with_ip(self, ip): entries = self.lobj.search_s(self.dn, ldap.SCOPE_SUBTREE, '(aRecord=%s)' % utils.utf8(ip)) objs = [] for entry in entries: if 'associatedDomain' in entry[1]: objs.append(HostEntry(self, entry)) return objs
def modify_address(self, name, address): names = self.ldap_tuple[1]['associatedDomain'] if not names: raise exception.NotFound() if len(names) == 1: self.lobj.modify_s(self.dn, [(ldap.MOD_REPLACE, 'aRecord', [utils.utf8(address)])]) else: self.remove_name(name) self.parent.add_entry(name, address)
def _get_tuple_for_domain(cls, lobj, domain): entry = lobj.search_s(CONF.ldap_dns_base_dn, ldap.SCOPE_SUBTREE, '(associatedDomain=%s)' % utils.utf8(domain)) if not entry: return None if len(entry) > 1: LOG.warning(_LW("Found multiple matches for domain " "%(domain)s.\n%(entry)s"), domain, entry) return entry[0]
def _add_location(robj): # Just in case... if 'server' not in robj.obj: return robj link = [l for l in robj.obj['server']['links'] if l['rel'] == 'self'] if link: robj['Location'] = utils.utf8(link[0]['href']) # Convenience return return robj
def _soa(cls): date = time.strftime('%Y%m%d%H%M%S') soa = '%s %s %s %s %s %s %s' % ( CONF.ldap_dns_servers[0], CONF.ldap_dns_soa_hostmaster, date, CONF.ldap_dns_soa_refresh, CONF.ldap_dns_soa_retry, CONF.ldap_dns_soa_expiry, CONF.ldap_dns_soa_minimum) return utils.utf8(soa)
def serialize(self, request, content_type): """Serializes the wrapped object. Utility method for serializing the wrapped object. Returns a webob.Response object. """ serializer = self.serializer body = None if self.obj is not None: body = serializer.serialize(self.obj) response = webob.Response(body=body) if response.headers.get('Content-Length'): # NOTE(andreykurilin): we need to encode 'Content-Length' header, # since webob.Response auto sets it if "body" attr is presented. # https://github.com/Pylons/webob/blob/1.5.0b0/webob/response.py#L147 response.headers['Content-Length'] = utils.utf8( response.headers['Content-Length']) response.status_int = self.code for hdr, value in self._headers.items(): response.headers[hdr] = utils.utf8(value) response.headers['Content-Type'] = utils.utf8(content_type) return response
def remove_name(self, name): names = self.ldap_tuple[1]['associatedDomain'] if not names: raise exception.NotFound() if len(names) > 1: # We just have to remove the requested domain. self.lobj.modify_s(self.dn, [(ldap.MOD_DELETE, 'associatedDomain', self._qualify(utils.utf8(name)))]) if (self.rdn[1] == name): # We just removed the rdn, so we need to move this entry. names.remove(self._qualify(name)) newrdn = 'dc=%s' % self._dequalify(names[0]) self.lobj.modrdn_s(self.dn, [newrdn]) else: # We should delete the entire record. self.lobj.delete_s(self.dn)
def _process_stack(self, request, action, action_args, content_type, body, accept): """Implement the processing stack.""" # Get the implementing method try: meth, extensions = self.get_method(request, action, content_type, body) except (AttributeError, TypeError): return Fault(webob.exc.HTTPNotFound()) except KeyError as ex: msg = _("There is no such action: %s") % ex.args[0] return Fault(webob.exc.HTTPBadRequest(explanation=msg)) except exception.MalformedRequestBody: msg = _("Malformed request body") return Fault(webob.exc.HTTPBadRequest(explanation=msg)) if body: msg = _("Action: '%(action)s', calling method: %(meth)s, body: " "%(body)s") % {'action': action, 'body': six.text_type(body, 'utf-8'), 'meth': str(meth)} LOG.debug(strutils.mask_password(msg)) else: LOG.debug("Calling method '%(meth)s'", {'meth': str(meth)}) # Now, deserialize the request body... try: contents = {} if self._should_have_body(request): # allow empty body with PUT and POST if request.content_length == 0: contents = {'body': None} else: contents = self.deserialize(body) except exception.MalformedRequestBody: msg = _("Malformed request body") return Fault(webob.exc.HTTPBadRequest(explanation=msg)) # Update the action args action_args.update(contents) project_id = action_args.pop("project_id", None) context = request.environ.get('compute.context') if (context and project_id and (project_id != context.project_id)): msg = _("Malformed request URL: URL's project_id '%(project_id)s'" " doesn't match Context's project_id" " '%(context_project_id)s'") % \ {'project_id': project_id, 'context_project_id': context.project_id} return Fault(webob.exc.HTTPBadRequest(explanation=msg)) # Run pre-processing extensions response, post = self.pre_process_extensions(extensions, request, action_args) if not response: try: with ResourceExceptionHandler(): action_result = self.dispatch(meth, request, action_args) except Fault as ex: response = ex if not response: # No exceptions; convert action_result into a # ResponseObject resp_obj = None if type(action_result) is dict or action_result is None: resp_obj = ResponseObject(action_result) elif isinstance(action_result, ResponseObject): resp_obj = action_result else: response = action_result # Run post-processing extensions if resp_obj: # Do a preserialize to set up the response object if hasattr(meth, 'wsgi_code'): resp_obj._default_code = meth.wsgi_code # Process post-processing extensions response = self.post_process_extensions(post, resp_obj, request, action_args) if resp_obj and not response: response = resp_obj.serialize(request, accept) if hasattr(response, 'headers'): for hdr, val in list(response.headers.items()): # Headers must be utf-8 strings response.headers[hdr] = utils.utf8(val) if not request.api_version_request.is_null(): response.headers[API_VERSION_REQUEST_HEADER] = \ request.api_version_request.get_string() response.headers['Vary'] = API_VERSION_REQUEST_HEADER return response
def _process_stack(self, request, action, action_args, content_type, body, accept): """Implement the processing stack.""" # Get the implementing method try: meth, extensions = self.get_method(request, action, content_type, body) except (AttributeError, TypeError): return Fault(webob.exc.HTTPNotFound()) except KeyError as ex: msg = _("There is no such action: %s") % ex.args[0] return Fault(webob.exc.HTTPBadRequest(explanation=msg)) except exception.MalformedRequestBody: msg = _("Malformed request body") return Fault(webob.exc.HTTPBadRequest(explanation=msg)) if body: msg = _("Action: '%(action)s', calling method: %(meth)s, body: " "%(body)s") % { 'action': action, 'body': six.text_type(body, 'utf-8'), 'meth': str(meth) } LOG.debug(strutils.mask_password(msg)) else: LOG.debug("Calling method '%(meth)s'", {'meth': str(meth)}) # Now, deserialize the request body... try: contents = {} if self._should_have_body(request): # allow empty body with PUT and POST if request.content_length == 0: contents = {'body': None} else: contents = self.deserialize(body) except exception.MalformedRequestBody: msg = _("Malformed request body") return Fault(webob.exc.HTTPBadRequest(explanation=msg)) # Update the action args action_args.update(contents) project_id = action_args.pop("project_id", None) context = request.environ.get('compute.context') if (context and project_id and (project_id != context.project_id)): msg = _("Malformed request URL: URL's project_id '%(project_id)s'" " doesn't match Context's project_id" " '%(context_project_id)s'") % \ {'project_id': project_id, 'context_project_id': context.project_id} return Fault(webob.exc.HTTPBadRequest(explanation=msg)) # Run pre-processing extensions response, post = self.pre_process_extensions(extensions, request, action_args) if not response: try: with ResourceExceptionHandler(): action_result = self.dispatch(meth, request, action_args) except Fault as ex: response = ex if not response: # No exceptions; convert action_result into a # ResponseObject resp_obj = None if type(action_result) is dict or action_result is None: resp_obj = ResponseObject(action_result) elif isinstance(action_result, ResponseObject): resp_obj = action_result else: response = action_result # Run post-processing extensions if resp_obj: # Do a preserialize to set up the response object if hasattr(meth, 'wsgi_code'): resp_obj._default_code = meth.wsgi_code # Process post-processing extensions response = self.post_process_extensions( post, resp_obj, request, action_args) if resp_obj and not response: response = resp_obj.serialize(request, accept) if hasattr(response, 'headers'): for hdr, val in list(response.headers.items()): # Headers must be utf-8 strings response.headers[hdr] = utils.utf8(val) if not request.api_version_request.is_null(): response.headers[API_VERSION_REQUEST_HEADER] = \ request.api_version_request.get_string() response.headers['Vary'] = API_VERSION_REQUEST_HEADER return response