Merge "L3 Metering label as shared"
This commit is contained in:
commit
bb536a3f4d
@ -54,6 +54,7 @@ class MeteringLabel(model_base.BASEV2, models_v2.HasId, models_v2.HasTenant):
|
||||
primaryjoin="MeteringLabel.tenant_id==Router.tenant_id",
|
||||
foreign_keys='MeteringLabel.tenant_id',
|
||||
uselist=True)
|
||||
shared = sa.Column(sa.Boolean, default=False, server_default=sql.false())
|
||||
|
||||
|
||||
class MeteringDbMixin(metering.MeteringPluginBase,
|
||||
@ -66,6 +67,7 @@ class MeteringDbMixin(metering.MeteringPluginBase,
|
||||
res = {'id': metering_label['id'],
|
||||
'name': metering_label['name'],
|
||||
'description': metering_label['description'],
|
||||
'shared': metering_label['shared'],
|
||||
'tenant_id': metering_label['tenant_id']}
|
||||
return self._fields(res, fields)
|
||||
|
||||
@ -77,7 +79,8 @@ class MeteringDbMixin(metering.MeteringPluginBase,
|
||||
metering_db = MeteringLabel(id=uuidutils.generate_uuid(),
|
||||
description=m['description'],
|
||||
tenant_id=tenant_id,
|
||||
name=m['name'])
|
||||
name=m['name'],
|
||||
shared=m['shared'])
|
||||
context.session.add(metering_db)
|
||||
|
||||
return self._make_metering_label_dict(metering_db)
|
||||
@ -207,10 +210,19 @@ class MeteringDbMixin(metering.MeteringPluginBase,
|
||||
|
||||
return res
|
||||
|
||||
def _process_sync_metering_data(self, labels):
|
||||
def _process_sync_metering_data(self, context, labels):
|
||||
all_routers = None
|
||||
|
||||
routers_dict = {}
|
||||
for label in labels:
|
||||
routers = label.routers
|
||||
if label.shared:
|
||||
if not all_routers:
|
||||
all_routers = self._get_collection_query(context,
|
||||
l3_db.Router)
|
||||
routers = all_routers
|
||||
else:
|
||||
routers = label.routers
|
||||
|
||||
for router in routers:
|
||||
router_dict = routers_dict.get(
|
||||
router['id'],
|
||||
@ -234,4 +246,4 @@ class MeteringDbMixin(metering.MeteringPluginBase,
|
||||
labels = (labels.join(MeteringLabel.routers).
|
||||
filter(l3_db.Router.id.in_(router_ids)))
|
||||
|
||||
return self._process_sync_metering_data(labels)
|
||||
return self._process_sync_metering_data(context, labels)
|
||||
|
@ -0,0 +1,39 @@
|
||||
# Copyright 2014 OpenStack Foundation
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
#
|
||||
|
||||
"""metering_label_shared
|
||||
|
||||
Revision ID: 3c346828361e
|
||||
Revises: 16a27a58e093
|
||||
Create Date: 2014-08-27 15:03:46.537290
|
||||
|
||||
"""
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '3c346828361e'
|
||||
down_revision = '16a27a58e093'
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
|
||||
def upgrade(active_plugins=None, options=None):
|
||||
op.add_column('meteringlabels', sa.Column('shared', sa.Boolean(),
|
||||
server_default=sa.sql.false(),
|
||||
nullable=True))
|
||||
|
||||
|
||||
def downgrade(active_plugins=None, options=None):
|
||||
op.drop_column('meteringlabels', 'shared')
|
@ -1 +1 @@
|
||||
16a27a58e093
|
||||
3c346828361e
|
||||
|
@ -51,13 +51,16 @@ RESOURCE_ATTRIBUTE_MAP = {
|
||||
'id': {'allow_post': False, 'allow_put': False,
|
||||
'is_visible': True,
|
||||
'primary_key': True},
|
||||
'name': {'allow_post': True, 'allow_put': True,
|
||||
'name': {'allow_post': True, 'allow_put': False,
|
||||
'is_visible': True, 'default': ''},
|
||||
'description': {'allow_post': True, 'allow_put': True,
|
||||
'description': {'allow_post': True, 'allow_put': False,
|
||||
'is_visible': True, 'default': ''},
|
||||
'tenant_id': {'allow_post': True, 'allow_put': False,
|
||||
'required_by_policy': True,
|
||||
'is_visible': True}
|
||||
'is_visible': True},
|
||||
'shared': {'allow_post': True, 'allow_put': False,
|
||||
'is_visible': True, 'default': False,
|
||||
'convert_to': attr.convert_to_boolean}
|
||||
},
|
||||
'metering_label_rules': {
|
||||
'id': {'allow_post': False, 'allow_put': False,
|
||||
@ -66,10 +69,10 @@ RESOURCE_ATTRIBUTE_MAP = {
|
||||
'metering_label_id': {'allow_post': True, 'allow_put': False,
|
||||
'validate': {'type:uuid': None},
|
||||
'is_visible': True, 'required_by_policy': True},
|
||||
'direction': {'allow_post': True, 'allow_put': True,
|
||||
'direction': {'allow_post': True, 'allow_put': False,
|
||||
'is_visible': True,
|
||||
'validate': {'type:values': ['ingress', 'egress']}},
|
||||
'excluded': {'allow_post': True, 'allow_put': True,
|
||||
'excluded': {'allow_post': True, 'allow_put': False,
|
||||
'is_visible': True, 'default': False,
|
||||
'convert_to': attr.convert_to_boolean},
|
||||
'remote_ip_prefix': {'allow_post': True, 'allow_put': False,
|
||||
|
@ -40,6 +40,7 @@ class MeteringPluginDbTestCaseMixin(object):
|
||||
data = {'metering_label': {'name': name,
|
||||
'tenant_id': kwargs.get('tenant_id',
|
||||
'test-tenant'),
|
||||
'shared': kwargs.get('shared', False),
|
||||
'description': description}}
|
||||
req = self.new_create_request('metering-labels', data,
|
||||
fmt)
|
||||
@ -149,6 +150,17 @@ class TestMetering(MeteringPluginDbTestCase):
|
||||
for k, v, in keys:
|
||||
self.assertEqual(metering_label['metering_label'][k], v)
|
||||
|
||||
def test_create_metering_label_shared(self):
|
||||
name = 'my label'
|
||||
description = 'my metering label'
|
||||
shared = True
|
||||
keys = [('name', name,), ('description', description),
|
||||
('shared', shared)]
|
||||
with self.metering_label(name, description,
|
||||
shared=shared) as metering_label:
|
||||
for k, v, in keys:
|
||||
self.assertEqual(metering_label['metering_label'][k], v)
|
||||
|
||||
def test_delete_metering_label(self):
|
||||
name = 'my label'
|
||||
description = 'my metering label'
|
||||
|
@ -120,6 +120,32 @@ class TestMeteringPlugin(test_db_plugin.NeutronDbPluginV2TestCase,
|
||||
set_context=True):
|
||||
self.mock_fanout.assert_called_with(self.ctx, expected)
|
||||
|
||||
def test_add_metering_label_shared_rpc_call(self):
|
||||
second_uuid = 'e27fe2df-376e-4ac7-ae13-92f050a21f84'
|
||||
expected = {'args': {'routers': [{'status': 'ACTIVE',
|
||||
'name': 'router1',
|
||||
'gw_port_id': None,
|
||||
'admin_state_up': True,
|
||||
'tenant_id': self.tenant_id,
|
||||
'_metering_labels': [
|
||||
{'rules': [],
|
||||
'id': self.uuid},
|
||||
{'rules': [],
|
||||
'id': second_uuid}],
|
||||
'id': self.uuid}]},
|
||||
'namespace': None,
|
||||
'method': 'add_metering_label'}
|
||||
|
||||
tenant_id_2 = '8a268a58-1610-4890-87e0-07abb8231206'
|
||||
with self.router(name='router1', tenant_id=self.tenant_id,
|
||||
set_context=True):
|
||||
with self.metering_label(tenant_id=self.tenant_id,
|
||||
set_context=True):
|
||||
self.mock_uuid.return_value = second_uuid
|
||||
with self.metering_label(tenant_id=tenant_id_2, shared=True,
|
||||
set_context=True):
|
||||
self.mock_fanout.assert_called_with(self.ctx, expected)
|
||||
|
||||
def test_remove_metering_label_rpc_call(self):
|
||||
expected = {'args':
|
||||
{'routers': [{'status': 'ACTIVE',
|
||||
@ -401,6 +427,10 @@ class TestMeteringPluginRpcFromL3Agent(
|
||||
self.meter_plugin = manager.NeutronManager.get_service_plugins().get(
|
||||
constants.METERING)
|
||||
|
||||
self.tenant_id = 'admin_tenant_id'
|
||||
self.tenant_id_1 = 'tenant_id_1'
|
||||
self.tenant_id_2 = 'tenant_id_2'
|
||||
|
||||
self.adminContext = context.get_admin_context()
|
||||
self._register_l3_agent('agent1')
|
||||
|
||||
@ -439,3 +469,29 @@ class TestMeteringPluginRpcFromL3Agent(
|
||||
|
||||
self._remove_external_gateway_from_router(
|
||||
r['id'], s['network_id'])
|
||||
|
||||
def test_get_sync_data_metering_shared(self):
|
||||
with self.router(name='router1', tenant_id=self.tenant_id_1):
|
||||
with self.router(name='router2', tenant_id=self.tenant_id_2):
|
||||
with self.metering_label(tenant_id=self.tenant_id,
|
||||
shared=True):
|
||||
callbacks = metering_rpc.MeteringRpcCallbacks(
|
||||
self.meter_plugin)
|
||||
data = callbacks.get_sync_data_metering(self.adminContext)
|
||||
|
||||
routers = [router['name'] for router in data]
|
||||
|
||||
self.assertIn('router1', routers)
|
||||
self.assertIn('router2', routers)
|
||||
|
||||
def test_get_sync_data_metering_not_shared(self):
|
||||
with self.router(name='router1', tenant_id=self.tenant_id_1):
|
||||
with self.router(name='router2', tenant_id=self.tenant_id_2):
|
||||
with self.metering_label(tenant_id=self.tenant_id):
|
||||
callbacks = metering_rpc.MeteringRpcCallbacks(
|
||||
self.meter_plugin)
|
||||
data = callbacks.get_sync_data_metering(self.adminContext)
|
||||
|
||||
routers = [router['name'] for router in data]
|
||||
|
||||
self.assertEqual([], routers)
|
||||
|
Loading…
Reference in New Issue
Block a user