Example #1
0
    def update_network(self, context, id, network):
        """Update Quantum network.

        Update an existing Quantum network and its corresponding MidoNet
        bridge.
        """
        LOG.debug(
            _("MidonetPluginV2.update_network called: id=%(id)r, "
              "network=%(network)r"), {
                  'id': id,
                  'network': network
              })

        # Reject admin_state_up=False
        if network['network'].get('admin_state_up') and network['network'][
                'admin_state_up'] is False:
            raise q_exc.NotImplementedError(
                _('admin_state_up=False '
                  'networks are not '
                  'supported.'))

        session = context.session
        with session.begin(subtransactions=True):
            net = super(MidonetPluginV2,
                        self).update_network(context, id, network)
            self.client.update_bridge(id, net['name'])

        self._extend_network_dict_l3(context, net)
        LOG.debug(_("MidonetPluginV2.update_network exiting: net=%r"), net)
        return net
Example #2
0
 def _port_view(self, request, tenant_id, network_id, port_id):
     """Returns udp port info for a given port"""
     if not hasattr(self._plugin, "get_udp_port"):
         return faults.Quantum11HTTPError(
             qexception.NotImplementedError("get_udp_port"))
     udp_port = self._plugin.get_udp_port(tenant_id, network_id, port_id)
     return dict(udp_port)
Example #3
0
 def _port_view(self, request, tenant_id, network_id, port_id):
     """Returns udp port info for a given port"""
     if not hasattr(self._plugin, "get_port_attrs"):
         return faults.Quantum11HTTPError(
             qexception.NotImplementedError("get_port_attrs"))
     meta = self._plugin.get_port_attrs(tenant_id, network_id, port_id)
     return {'attributes': meta, 'id': port_id}
Example #4
0
    def create_subnet(self, context, subnet):
        """Create Quantum subnet.

        Creates a Quantum subnet and a DHCP entry in MidoNet bridge.
        """
        LOG.debug(_("MidonetPluginV2.create_subnet called: subnet=%r"), subnet)

        if subnet['subnet']['ip_version'] == 6:
            raise q_exc.NotImplementedError(_("MidoNet doesn't support IPv6."))

        net = super(MidonetPluginV2,
                    self).get_network(context,
                                      subnet['subnet']['network_id'],
                                      fields=None)
        if net['subnets']:
            raise q_exc.NotImplementedError(
                _("MidoNet doesn't support multiple subnets "
                  "on the same network."))

        session = context.session
        with session.begin(subtransactions=True):
            sn_entry = super(MidonetPluginV2,
                             self).create_subnet(context, subnet)
            bridge = self.client.get_bridge(sn_entry['network_id'])

            gateway_ip = subnet['subnet']['gateway_ip']
            network_address, prefix = subnet['subnet']['cidr'].split('/')
            self.client.create_dhcp(bridge, gateway_ip, network_address,
                                    prefix)

            # For external network, link the bridge to the provider router.
            self._extend_network_dict_l3(context, net)
            if net['router:external']:
                gateway_ip = sn_entry['gateway_ip']
                network_address, length = sn_entry['cidr'].split('/')

                self.client.link_bridge_to_provider_router(
                    bridge, self.provider_router, gateway_ip, network_address,
                    length)

        LOG.debug(_("MidonetPluginV2.create_subnet exiting: sn_entry=%r"),
                  sn_entry)
        return sn_entry
Example #5
0
    def _show(self, request, tenant_id, network_id, port_id):
        """Returns port statistics for a given port"""
        if not hasattr(self._plugin, "get_port_stats"):
            return faults.QuantumHTTPError(
                qexception.NotImplementedError("get_port_stats"))

        stats = self._plugin.get_port_stats(tenant_id, network_id, port_id)
        builder = portstats_view.get_view_builder(request)
        result = builder.build(stats, True)
        return dict(stats=result)
Example #6
0
    def test_create_network_quota_no_counts(self):
        cfg.CONF.set_override('quota_network', 1, group='QUOTAS')
        initial_input = {'network': {'name': 'net1', 'tenant_id': _uuid()}}
        full_input = {'network': {'admin_state_up': True, 'subnets': []}}
        full_input['network'].update(initial_input['network'])

        instance = self.plugin.return_value
        instance.get_networks_count.side_effect = (q_exc.NotImplementedError())
        instance.get_networks.return_value = ["foo"]
        res = self.api.post_json(_get_path('networks'),
                                 initial_input,
                                 expect_errors=True)
        instance.get_networks_count.assert_called_with(mock.ANY,
                                                       filters=mock.ANY)
        self.assertTrue(
            "Quota exceeded for resources" in res.json['QuantumError'])
Example #7
0
    def get_ports_count(self, context, filters=None):
        """Return the number of ports.

        The result depends on the identity of the user making the request
        (as indicated by the context) as well as any filters.
        : param context: quantum api request context
        : param filters: a dictionary with keys that are valid keys for
            a network as listed in the RESOURCE_ATTRIBUTE_MAP object
            in quantum/api/v2/attributes.py.  Values in this dictiontary
            are an iterable containing values that will be used for an exact
            match comparison for that value.  Each result returned by this
            function will have matched one of the values for each key in
            filters.

        NOTE: this method is optional, as it was not part of the originally
              defined plugin API.
        """
        raise exceptions.NotImplementedError()
Example #8
0
    def update_network(self, context, id, network):
        """
        Updates the properties of a particular Virtual Network.

        :returns: a sequence of mappings with the following signature:
        {'id': UUID representing the network.
         'name': Human-readable name identifying the network.
         'tenant_id': Owner of network. only admin user
                      can specify a tenant_id other than its own.
        'admin_state_up': Sets admin state of network. if down,
                          network does not forward packets.
        'status': Indicates whether network is currently
                  operational (limit values to "ACTIVE", "DOWN",
                               "BUILD", and "ERROR"?
        'subnets': Subnets associated with this network. Plan
                   to allow fully specified subnets as part of
                   network create.
                   }

        :raises: exception.NetworkNotFound
        :raises: exception.NoImplementedError
        """

        if network["network"].get("admin_state_up"):
            if network['network']["admin_state_up"] is False:
                raise exception.NotImplementedError("admin_state_up=False "
                                                    "networks are not "
                                                    "supported.")
        params = {}
        params["network"] = network["network"]
        pairs = self._get_lswitch_cluster_pairs(id, context.tenant_id)

        #Only field to update in NVP is name
        if network['network'].get("name"):
            for (cluster, switches) in pairs:
                for switch in switches:
                    result = nvplib.update_network(cluster, switch, **params)

        LOG.debug("update_network() completed for tenant: %s" %
                  context.tenant_id)
        return super(NvpPluginV2, self).update_network(context, id, network)
Example #9
0
 def get_floatingips_count(self, context, filters=None):
     raise qexception.NotImplementedError()
Example #10
0
    def update_router(self, context, id, router):
        LOG.debug(
            _("MidonetPluginV2.update_router called: id=%(id)s "
              "router=%(router)r"), router)

        if router['router'].get('admin_state_up') is False:
            raise q_exc.NotImplementedError(
                _('admin_state_up=False '
                  'routers are not '
                  'supported.'))

        op_gateway_set = False
        op_gateway_clear = False

        # figure out which operation it is in
        if ('external_gateway_info' in router['router']
                and 'network_id' in router['router']['external_gateway_info']):
            op_gateway_set = True
        elif ('external_gateway_info' in router['router']
              and router['router']['external_gateway_info'] == {}):
            op_gateway_clear = True

            qports = super(MidonetPluginV2,
                           self).get_ports(context, {
                               'device_id': [id],
                               'device_owner': ['network:router_gateway']
                           })

            assert len(qports) == 1
            qport = qports[0]
            snat_ip = qport['fixed_ips'][0]['ip_address']
            qport['network_id']

        session = context.session
        with session.begin(subtransactions=True):

            qrouter = super(MidonetPluginV2,
                            self).update_router(context, id, router)

            changed_name = router['router'].get('name')
            if changed_name:
                self.client.update_router(id, changed_name)

            if op_gateway_set:
                # find a qport with the network_id for the router
                qports = super(MidonetPluginV2,
                               self).get_ports(context, {
                                   'device_id': [id],
                                   'device_owner': ['network:router_gateway']
                               })
                assert len(qports) == 1
                qport = qports[0]
                snat_ip = qport['fixed_ips'][0]['ip_address']

                self.client.set_router_external_gateway(
                    id, self.provider_router, snat_ip)

            if op_gateway_clear:
                self.client.clear_router_external_gateway(id)

        LOG.debug(_("MidonetPluginV2.update_router exiting: qrouter=%r"),
                  qrouter)
        return qrouter
Example #11
0
 def notimplemented_function(self, request, id):
     return faults.Quantum10HTTPError(
         exceptions.NotImplementedError("notimplemented_function"))
Example #12
0
    def create_subnet(self, context, subnet):
        """Create Quantum subnet.

        Creates a Quantum subnet and a DHCP entry in MidoNet bridge.
        """
        LOG.debug(_("MidonetPluginV2.create_subnet called: subnet=%r"), subnet)

        if subnet['subnet']['ip_version'] == 6:
            raise q_exc.NotImplementedError(_("MidoNet doesn't support IPv6."))

        net = super(MidonetPluginV2,
                    self).get_network(context,
                                      subnet['subnet']['network_id'],
                                      fields=None)
        if net['subnets']:
            raise q_exc.NotImplementedError(
                _("MidoNet doesn't support multiple subnets "
                  "on the same network."))

        session = context.session
        with session.begin(subtransactions=True):
            sn_entry = super(MidonetPluginV2,
                             self).create_subnet(context, subnet)
            try:
                bridge = self.mido_api.get_bridge(sn_entry['network_id'])
            except w_exc.HTTPNotFound:
                raise MidonetResourceNotFound(resource_type='Bridge',
                                              id=sn_entry['network_id'])

            gateway_ip = subnet['subnet']['gateway_ip']
            network_address, prefix = subnet['subnet']['cidr'].split('/')
            bridge.add_dhcp_subnet().default_gateway(gateway_ip).subnet_prefix(
                network_address).subnet_length(prefix).create()

            # If the network is external, link the bridge to MidoNet provider
            # router
            self._extend_network_dict_l3(context, net)
            if net['router:external']:
                gateway_ip = sn_entry['gateway_ip']
                network_address, length = sn_entry['cidr'].split('/')

                # create a interior port in the MidoNet provider router
                in_port = self.provider_router.add_interior_port()
                pr_port = in_port.port_address(gateway_ip).network_address(
                    network_address).network_length(length).create()

                # create a interior port in the bridge, then link
                # it to the provider router.
                br_port = bridge.add_interior_port().create()
                pr_port.link(br_port.get_id())

                # add a route for the subnet in the provider router
                self.provider_router.add_route().type(
                    'Normal').src_network_addr('0.0.0.0').src_network_length(
                        0).dst_network_addr(
                            network_address).dst_network_length(length).weight(
                                100).next_hop_port(pr_port.get_id()).create()

        LOG.debug(_("MidonetPluginV2.create_subnet exiting: sn_entry=%r"),
                  sn_entry)
        return sn_entry
Example #13
0
    def update_router(self, context, id, router):
        LOG.debug(
            _("MidonetPluginV2.update_router called: id=%(id)s "
              "router=%(router)r"), router)

        if router['router'].get('admin_state_up') is False:
            raise q_exc.NotImplementedError(
                _('admin_state_up=False '
                  'routers are not '
                  'supported.'))

        op_gateway_set = False
        op_gateway_clear = False

        # figure out which operation it is in
        if ('external_gateway_info' in router['router']
                and 'network_id' in router['router']['external_gateway_info']):
            op_gateway_set = True
        elif ('external_gateway_info' in router['router']
              and router['router']['external_gateway_info'] == {}):
            op_gateway_clear = True

            qports = super(MidonetPluginV2,
                           self).get_ports(context, {
                               'device_id': [id],
                               'device_owner': ['network:router_gateway']
                           })

            assert len(qports) == 1
            qport = qports[0]
            snat_ip = qport['fixed_ips'][0]['ip_address']
            qport['network_id']

        session = context.session
        with session.begin(subtransactions=True):

            qrouter = super(MidonetPluginV2,
                            self).update_router(context, id, router)

            changed_name = router['router'].get('name')
            if changed_name:
                self.mido_api.get_router(id).name(changed_name).update()

            tenant_router = self.mido_api.get_router(id)
            if op_gateway_set:
                # find a qport with the network_id for the router
                qports = super(MidonetPluginV2,
                               self).get_ports(context, {
                                   'device_id': [id],
                                   'device_owner': ['network:router_gateway']
                               })
                assert len(qports) == 1
                qport = qports[0]
                snat_ip = qport['fixed_ips'][0]['ip_address']

                in_port = self.provider_router.add_interior_port()
                pr_port = in_port.network_address(
                    '169.254.255.0').network_length(30).port_address(
                        '169.254.255.1').create()

                # Create a port in the tenant router
                tr_port = tenant_router.add_interior_port().network_address(
                    '169.254.255.0').network_length(30).port_address(
                        '169.254.255.2').create()

                # Link them
                pr_port.link(tr_port.get_id())

                # Add a route for snat_ip to bring it down to tenant
                self.provider_router.add_route().type(
                    'Normal').src_network_addr('0.0.0.0').src_network_length(
                        0).dst_network_addr(snat_ip).dst_network_length(
                            32).weight(100).next_hop_port(
                                pr_port.get_id()).create()

                # Add default route to uplink in the tenant router
                tenant_router.add_route().type('Normal').src_network_addr(
                    '0.0.0.0').src_network_length(0).dst_network_addr(
                        '0.0.0.0').dst_network_length(0).weight(
                            100).next_hop_port(tr_port.get_id()).create()

                # ADD SNAT(masquerade) rules
                chains = self.chain_manager.get_router_chains(
                    tenant_router.get_tenant_id(), tenant_router.get_id())

                chains['in'].add_rule().nw_dst_address(snat_ip).nw_dst_length(
                    32).type('rev_snat').flow_action('accept').in_ports([
                        tr_port.get_id()
                    ]).properties(SNAT_RULE_PROPERTY).position(1).create()

                nat_targets = []
                nat_targets.append({
                    'addressFrom': snat_ip,
                    'addressTo': snat_ip,
                    'portFrom': 1,
                    'portTo': 65535
                })

                chains['out'].add_rule().type('snat').flow_action(
                    'accept').nat_targets(nat_targets).out_ports([
                        tr_port.get_id()
                    ]).properties(SNAT_RULE_PROPERTY).position(1).create()

            if op_gateway_clear:
                # delete the port that is connected to provider router
                for p in tenant_router.get_ports():
                    if p.get_port_address() == '169.254.255.2':
                        peer_port_id = p.get_peer_id()
                        p.unlink()
                        self.mido_api.get_port(peer_port_id).delete()
                        p.delete()

                # delete default route
                for r in tenant_router.get_routes():
                    if (r.get_dst_network_addr() == '0.0.0.0'
                            and r.get_dst_network_length() == 0):
                        r.delete()

                # delete SNAT(masquerade) rules
                chains = self.chain_manager.get_router_chains(
                    tenant_router.get_tenant_id(), tenant_router.get_id())

                for r in chains['in'].get_rules():
                    if OS_TENANT_ROUTER_RULE_KEY in r.get_properties():
                        if r.get_properties(
                        )[OS_TENANT_ROUTER_RULE_KEY] == SNAT_RULE:
                            r.delete()

                for r in chains['out'].get_rules():
                    if OS_TENANT_ROUTER_RULE_KEY in r.get_properties():
                        if r.get_properties(
                        )[OS_TENANT_ROUTER_RULE_KEY] == SNAT_RULE:
                            r.delete()

        LOG.debug(_("MidonetPluginV2.update_router exiting: qrouter=%r"),
                  qrouter)
        return qrouter