def create_route(context, route): LOG.info("create_route for tenant %s" % context.tenant_id) route = route["route"] for key in ["gateway", "cidr", "subnet_id"]: if key not in route: raise exceptions.BadRequest(resource="routes", msg="%s is required" % key) subnet_id = route["subnet_id"] with context.session.begin(): subnet = db_api.subnet_find(context, id=subnet_id, scope=db_api.ONE) if not subnet: raise exceptions.SubnetNotFound(subnet_id=subnet_id) policies = db_models.IPPolicy.get_ip_policy_cidrs(subnet) alloc_pools = allocation_pool.AllocationPools(subnet["cidr"], policies=policies) alloc_pools.validate_gateway_excluded(route["gateway"]) # TODO(anyone): May want to denormalize the cidr values into columns # to achieve single db lookup on conflict check route_cidr = netaddr.IPNetwork(route["cidr"]) subnet_routes = db_api.route_find(context, subnet_id=subnet_id, scope=db_api.ALL) quota.QUOTAS.limit_check(context, context.tenant_id, routes_per_subnet=len(subnet_routes) + 1) for sub_route in subnet_routes: sub_route_cidr = netaddr.IPNetwork(sub_route["cidr"]) if sub_route_cidr.value == DEFAULT_ROUTE.value: continue if route_cidr in sub_route_cidr or sub_route_cidr in route_cidr: raise quark_exceptions.RouteConflict(route_id=sub_route["id"], cidr=str(route_cidr)) new_route = db_api.route_create(context, **route) return v._make_route_dict(new_route)
def update_subnet(context, id, subnet): """Update values of a subnet. : param context: neutron api request context : param id: UUID representing the subnet to update. : param subnet: dictionary with keys indicating fields to update. valid keys are those that have a value of True for 'allow_put' as listed in the RESOURCE_ATTRIBUTE_MAP object in neutron/api/v2/attributes.py. """ LOG.info("update_subnet %s for tenant %s" % (id, context.tenant_id)) subnet_db = db_api.subnet_find(context, id=id, scope=db_api.ONE) if not subnet_db: raise exceptions.SubnetNotFound(id=id) s = subnet["subnet"] dns_ips = s.pop("dns_nameservers", []) host_routes = s.pop("host_routes", []) gateway_ip = s.pop("gateway_ip", None) if gateway_ip: default_route = None for route in host_routes: netaddr_route = netaddr.IPNetwork(route["destination"]) if netaddr_route.value == routes.DEFAULT_ROUTE.value: default_route = route break if default_route is None: route_model = db_api.route_find(context, cidr=str(routes.DEFAULT_ROUTE), subnet_id=id, scope=db_api.ONE) if route_model: db_api.route_update(context, route_model, gateway=gateway_ip) else: db_api.route_create(context, cidr=str(routes.DEFAULT_ROUTE), gateway=gateway_ip, subnet_id=id) if dns_ips: subnet_db["dns_nameservers"] = [] for dns_ip in dns_ips: subnet_db["dns_nameservers"].append( db_api.dns_create(context, ip=netaddr.IPAddress(dns_ip))) if host_routes: subnet_db["routes"] = [] for route in host_routes: subnet_db["routes"].append( db_api.route_create(context, cidr=route["destination"], gateway=route["nexthop"])) subnet = db_api.subnet_update(context, subnet_db, **s) return v._make_subnet_dict(subnet, default_route=routes.DEFAULT_ROUTE)
def update_subnet(context, id, subnet): """Update values of a subnet. : param context: neutron api request context : param id: UUID representing the subnet to update. : param subnet: dictionary with keys indicating fields to update. valid keys are those that have a value of True for 'allow_put' as listed in the RESOURCE_ATTRIBUTE_MAP object in neutron/api/v2/attributes.py. """ LOG.info("update_subnet %s for tenant %s" % (id, context.tenant_id)) with context.session.begin(): subnet_db = db_api.subnet_find(context, id=id, scope=db_api.ONE) if not subnet_db: raise exceptions.SubnetNotFound(id=id) s = subnet["subnet"] dns_ips = s.pop("dns_nameservers", []) host_routes = s.pop("host_routes", []) gateway_ip = s.pop("gateway_ip", None) if gateway_ip: default_route = None for route in host_routes: netaddr_route = netaddr.IPNetwork(route["destination"]) if netaddr_route.value == routes.DEFAULT_ROUTE.value: default_route = route break if default_route is None: route_model = db_api.route_find( context, cidr=str(routes.DEFAULT_ROUTE), subnet_id=id, scope=db_api.ONE) if route_model: db_api.route_update(context, route_model, gateway=gateway_ip) else: db_api.route_create(context, cidr=str(routes.DEFAULT_ROUTE), gateway=gateway_ip, subnet_id=id) if dns_ips: subnet_db["dns_nameservers"] = [] for dns_ip in dns_ips: subnet_db["dns_nameservers"].append(db_api.dns_create( context, ip=netaddr.IPAddress(dns_ip))) if host_routes: subnet_db["routes"] = [] for route in host_routes: subnet_db["routes"].append(db_api.route_create( context, cidr=route["destination"], gateway=route["nexthop"])) subnet = db_api.subnet_update(context, subnet_db, **s) return v._make_subnet_dict(subnet)
def delete_route(context, id): #TODO(mdietz): This is probably where we check to see that someone is # admin and only filter on tenant if they aren't. Correct # for all the above later LOG.info("delete_route %s for tenant %s" % (id, context.tenant_id)) route = db_api.route_find(context, id, scope=db_api.ONE) if not route: raise quark_exceptions.RouteNotFound(route_id=id) db_api.route_delete(context, route)
def _validate_policy_with_routes(context, policies, subnets): pools = {} policy_networks = [netaddr.IPNetwork(p) for p in policies] for subnet in subnets: pool = allocation_pool.AllocationPools(subnet["cidr"], policies=policy_networks) pools[subnet["id"]] = pool subnet_ids = [subnet["id"] for subnet in subnets] routes = db_api.route_find(context, subnet_id=subnet_ids) for route in routes: subnet_pool = pools[route["subnet_id"]] subnet_pool.validate_gateway_excluded(route["gateway"])
def create_route(context, route): LOG.info("create_route for tenant %s" % context.tenant_id) if not route: raise n_exc.BadRequest(resource="routes", msg="Malformed body") route = route.get("route") if not route: raise n_exc.BadRequest(resource="routes", msg="Malformed body") for key in ["gateway", "cidr", "subnet_id"]: if key not in route: raise n_exc.BadRequest(resource="routes", msg="%s is required" % key) subnet_id = route["subnet_id"] with context.session.begin(): subnet = db_api.subnet_find(context, id=subnet_id, scope=db_api.ONE) if not subnet: raise n_exc.SubnetNotFound(subnet_id=subnet_id) if subnet["ip_policy"]: policies = subnet["ip_policy"].get_cidrs_ip_set() else: policies = netaddr.IPSet([]) alloc_pools = allocation_pool.AllocationPools(subnet["cidr"], policies=policies) try: alloc_pools.validate_gateway_excluded(route["gateway"]) except neutron_exc.GatewayConflictWithAllocationPools as e: LOG.exception(str(e)) raise n_exc.BadRequest(resource="routes", msg=str(e)) # TODO(anyone): May want to denormalize the cidr values into columns # to achieve single db lookup on conflict check route_cidr = netaddr.IPNetwork(route["cidr"]) subnet_routes = db_api.route_find(context, subnet_id=subnet_id, scope=db_api.ALL) quota.QUOTAS.limit_check(context, context.tenant_id, routes_per_subnet=len(subnet_routes) + 1) for sub_route in subnet_routes: sub_route_cidr = netaddr.IPNetwork(sub_route["cidr"]) if sub_route_cidr.value == DEFAULT_ROUTE.value: continue if route_cidr in sub_route_cidr or sub_route_cidr in route_cidr: raise q_exc.RouteConflict(route_id=sub_route["id"], cidr=str(route_cidr)) new_route = db_api.route_create(context, **route) return v._make_route_dict(new_route)
def create_route(self, context, route): LOG.info("create_route for tenant %s" % context.tenant_id) route = route["route"] subnet_id = route["subnet_id"] subnet = db_api.subnet_find(context, id=id) if not subnet: raise exceptions.SubnetNotFound(subnet_id=subnet_id) # TODO(anyone): May need to denormalize the cidr values to achieve # single db lookup route_cidr = netaddr.IPNetwork(route["cidr"]) subnet_routes = db_api.route_find(context, subnet_id=subnet_id) for sub_route in subnet_routes: sub_route_cidr = netaddr.IPNetwork(sub_route["cidr"]) if route_cidr in sub_route_cidr or sub_route_cidr in route_cidr: raise quark_exceptions.RouteConflict(route_id=sub_route["id"], cidr=str(route_cidr)) new_route = db_api.route_create(context, **route) return self._make_route_dict(new_route)
def create_route(context, route): LOG.info("create_route for tenant %s" % context.tenant_id) route = route["route"] subnet_id = route["subnet_id"] subnet = db_api.subnet_find(context, id=subnet_id, scope=db_api.ONE) if not subnet: raise exceptions.SubnetNotFound(subnet_id=subnet_id) # TODO(anyone): May want to denormalize the cidr values into columns # to achieve single db lookup on conflict check route_cidr = netaddr.IPNetwork(route["cidr"]) subnet_routes = db_api.route_find(context, subnet_id=subnet_id, scope=db_api.ALL) for sub_route in subnet_routes: sub_route_cidr = netaddr.IPNetwork(sub_route["cidr"]) if sub_route_cidr.value == DEFAULT_ROUTE.value: continue if route_cidr in sub_route_cidr or sub_route_cidr in route_cidr: raise quark_exceptions.RouteConflict( route_id=sub_route["id"], cidr=str(route_cidr)) new_route = db_api.route_create(context, **route) return v._make_route_dict(new_route)
def create_route(context, route): LOG.info("create_route for tenant %s" % context.tenant_id) route = route["route"] subnet_id = route["subnet_id"] subnet = db_api.subnet_find(context, id=subnet_id, scope=db_api.ONE) if not subnet: raise exceptions.SubnetNotFound(subnet_id=subnet_id) # TODO(anyone): May want to denormalize the cidr values into columns # to achieve single db lookup on conflict check route_cidr = netaddr.IPNetwork(route["cidr"]) subnet_routes = db_api.route_find(context, subnet_id=subnet_id, scope=db_api.ALL) for sub_route in subnet_routes: sub_route_cidr = netaddr.IPNetwork(sub_route["cidr"]) if sub_route_cidr.value == DEFAULT_ROUTE.value: continue if route_cidr in sub_route_cidr or sub_route_cidr in route_cidr: raise quark_exceptions.RouteConflict(route_id=sub_route["id"], cidr=str(route_cidr)) new_route = db_api.route_create(context, **route) return v._make_route_dict(new_route)
def get_route(context, id): LOG.info("get_route %s for tenant %s" % (id, context.tenant_id)) route = db_api.route_find(context, id=id, scope=db_api.ONE) if not route: raise q_exc.RouteNotFound(route_id=id) return v._make_route_dict(route)
def update_subnet(context, id, subnet): """Update values of a subnet. : param context: neutron api request context : param id: UUID representing the subnet to update. : param subnet: dictionary with keys indicating fields to update. valid keys are those that have a value of True for 'allow_put' as listed in the RESOURCE_ATTRIBUTE_MAP object in neutron/api/v2/attributes.py. """ LOG.info("update_subnet %s for tenant %s" % (id, context.tenant_id)) with context.session.begin(): subnet_db = db_api.subnet_find(context, None, None, None, False, id=id, scope=db_api.ONE) if not subnet_db: raise exceptions.SubnetNotFound(id=id) s = subnet["subnet"] always_pop = ["_cidr", "cidr", "first_ip", "last_ip", "ip_version", "segment_id", "network_id"] admin_only = ["do_not_use", "created_at", "tenant_id", "next_auto_assign_ip", "enable_dhcp"] utils.filter_body(context, s, admin_only, always_pop) dns_ips = utils.pop_param(s, "dns_nameservers", []) host_routes = utils.pop_param(s, "host_routes", []) gateway_ip = utils.pop_param(s, "gateway_ip", None) allocation_pools = utils.pop_param(s, "allocation_pools", None) if not CONF.QUARK.allow_allocation_pool_update: if allocation_pools: raise exceptions.BadRequest( resource="subnets", msg="Allocation pools cannot be updated.") alloc_pools = allocation_pool.AllocationPools( subnet_db["cidr"], policies=models.IPPolicy.get_ip_policy_cidrs(subnet_db)) else: alloc_pools = allocation_pool.AllocationPools(subnet_db["cidr"], allocation_pools) quota.QUOTAS.limit_check( context, context.tenant_id, alloc_pools_per_subnet=len(alloc_pools)) if gateway_ip: alloc_pools.validate_gateway_excluded(gateway_ip) default_route = None for route in host_routes: netaddr_route = netaddr.IPNetwork(route["destination"]) if netaddr_route.value == routes.DEFAULT_ROUTE.value: default_route = route break if default_route is None: route_model = db_api.route_find( context, cidr=str(routes.DEFAULT_ROUTE), subnet_id=id, scope=db_api.ONE) if route_model: db_api.route_update(context, route_model, gateway=gateway_ip) else: db_api.route_create(context, cidr=str(routes.DEFAULT_ROUTE), gateway=gateway_ip, subnet_id=id) if dns_ips: subnet_db["dns_nameservers"] = [] quota.QUOTAS.limit_check(context, context.tenant_id, dns_nameservers_per_subnet=len(dns_ips)) for dns_ip in dns_ips: subnet_db["dns_nameservers"].append(db_api.dns_create( context, ip=netaddr.IPAddress(dns_ip))) if host_routes: subnet_db["routes"] = [] quota.QUOTAS.limit_check(context, context.tenant_id, routes_per_subnet=len(host_routes)) for route in host_routes: subnet_db["routes"].append(db_api.route_create( context, cidr=route["destination"], gateway=route["nexthop"])) if CONF.QUARK.allow_allocation_pool_update: if isinstance(allocation_pools, list): cidrs = alloc_pools.get_policy_cidrs() ip_policies.ensure_default_policy(cidrs, [subnet_db]) subnet_db["ip_policy"] = db_api.ip_policy_update( context, subnet_db["ip_policy"], exclude=cidrs) # invalidate the cache db_api.subnet_update_set_alloc_pool_cache(context, subnet_db) subnet = db_api.subnet_update(context, subnet_db, **s) return v._make_subnet_dict(subnet)
def update_subnet(context, id, subnet): """Update values of a subnet. : param context: neutron api request context : param id: UUID representing the subnet to update. : param subnet: dictionary with keys indicating fields to update. valid keys are those that have a value of True for 'allow_put' as listed in the RESOURCE_ATTRIBUTE_MAP object in neutron/api/v2/attributes.py. """ LOG.info("update_subnet %s for tenant %s" % (id, context.tenant_id)) with context.session.begin(): subnet_db = db_api.subnet_find(context, None, None, None, False, id=id, scope=db_api.ONE) if not subnet_db: raise exceptions.SubnetNotFound(id=id) s = subnet["subnet"] always_pop = [ "_cidr", "cidr", "first_ip", "last_ip", "ip_version", "segment_id", "network_id" ] admin_only = [ "do_not_use", "created_at", "tenant_id", "next_auto_assign_ip", "enable_dhcp" ] utils.filter_body(context, s, admin_only, always_pop) dns_ips = utils.pop_param(s, "dns_nameservers", []) host_routes = utils.pop_param(s, "host_routes", []) gateway_ip = utils.pop_param(s, "gateway_ip", None) allocation_pools = utils.pop_param(s, "allocation_pools", None) if not CONF.QUARK.allow_allocation_pool_update: if allocation_pools: raise exceptions.BadRequest( resource="subnets", msg="Allocation pools cannot be updated.") alloc_pools = allocation_pool.AllocationPools( subnet_db["cidr"], policies=models.IPPolicy.get_ip_policy_cidrs(subnet_db)) else: alloc_pools = allocation_pool.AllocationPools( subnet_db["cidr"], allocation_pools) quota.QUOTAS.limit_check(context, context.tenant_id, alloc_pools_per_subnet=len(alloc_pools)) if gateway_ip: alloc_pools.validate_gateway_excluded(gateway_ip) default_route = None for route in host_routes: netaddr_route = netaddr.IPNetwork(route["destination"]) if netaddr_route.value == routes.DEFAULT_ROUTE.value: default_route = route break if default_route is None: route_model = db_api.route_find(context, cidr=str(routes.DEFAULT_ROUTE), subnet_id=id, scope=db_api.ONE) if route_model: db_api.route_update(context, route_model, gateway=gateway_ip) else: db_api.route_create(context, cidr=str(routes.DEFAULT_ROUTE), gateway=gateway_ip, subnet_id=id) if dns_ips: subnet_db["dns_nameservers"] = [] quota.QUOTAS.limit_check(context, context.tenant_id, dns_nameservers_per_subnet=len(dns_ips)) for dns_ip in dns_ips: subnet_db["dns_nameservers"].append( db_api.dns_create(context, ip=netaddr.IPAddress(dns_ip))) if host_routes: subnet_db["routes"] = [] quota.QUOTAS.limit_check(context, context.tenant_id, routes_per_subnet=len(host_routes)) for route in host_routes: subnet_db["routes"].append( db_api.route_create(context, cidr=route["destination"], gateway=route["nexthop"])) if CONF.QUARK.allow_allocation_pool_update: if isinstance(allocation_pools, list): cidrs = alloc_pools.get_policy_cidrs() ip_policies.ensure_default_policy(cidrs, [subnet_db]) subnet_db["ip_policy"] = db_api.ip_policy_update( context, subnet_db["ip_policy"], exclude=cidrs) # invalidate the cache db_api.subnet_update_set_alloc_pool_cache(context, subnet_db) subnet = db_api.subnet_update(context, subnet_db, **s) return v._make_subnet_dict(subnet)
def get_route(context, id): LOG.info("get_route %s for tenant %s" % (id, context.tenant_id)) route = db_api.route_find(context, id=id, scope=db_api.ONE) if not route: raise quark_exceptions.RouteNotFound(route_id=id) return v._make_route_dict(route)
def get_routes(context): LOG.info("get_routes for tenant %s" % context.tenant_id) routes = db_api.route_find(context) return [v._make_route_dict(r) for r in routes]
def get_route(self, context, id): LOG.info("get_route %s for tenant %s" % (id, context.tenant_id)) route = db_api.route_find(context, id=id) if not route: raise quark_exceptions.RouteNotFound(route_id=id) return self._make_route_dict(route)