summaryrefslogtreecommitdiff
path: root/openstackclient/network
diff options
context:
space:
mode:
authorJenkins <jenkins@review.openstack.org>2016-03-04 23:39:22 +0000
committerGerrit Code Review <review@openstack.org>2016-03-04 23:39:22 +0000
commita61c5cc8a4884fd97d0938b3559f6a630cd4ad50 (patch)
treeb40156e012f2eee95f76303c277ff5d7955ba157 /openstackclient/network
parent5c1633f5050a21ad1866eb3056df74595780e5ae (diff)
parentd1d4a40808741c416ecc51294fab78138f9184fa (diff)
downloadpython-openstackclient-a61c5cc8a4884fd97d0938b3559f6a630cd4ad50.tar.gz
Merge "Add 'port create' command"
Diffstat (limited to 'openstackclient/network')
-rw-r--r--openstackclient/network/v2/port.py171
1 files changed, 168 insertions, 3 deletions
diff --git a/openstackclient/network/v2/port.py b/openstackclient/network/v2/port.py
index 19b3701d..f9d0fc95 100644
--- a/openstackclient/network/v2/port.py
+++ b/openstackclient/network/v2/port.py
@@ -14,13 +14,14 @@
"""Port action implementations"""
from openstackclient.common import command
+from openstackclient.common import parseractions
from openstackclient.common import utils
+from openstackclient.identity import common as identity_common
def _format_admin_state(state):
return 'UP' if state else 'DOWN'
-
_formatters = {
'admin_state_up': _format_admin_state,
'allowed_address_pairs': utils.format_list_of_dicts,
@@ -49,7 +50,171 @@ def _get_columns(item):
if binding_column in columns:
columns.remove(binding_column)
columns.append(binding_column.replace('binding:', 'binding_', 1))
- return sorted(columns)
+ return tuple(sorted(columns))
+
+
+def _get_attrs(client_manager, parsed_args):
+ attrs = {}
+
+ if parsed_args.name is not None:
+ attrs['name'] = str(parsed_args.name)
+ if parsed_args.fixed_ip is not None:
+ attrs['fixed_ips'] = parsed_args.fixed_ip
+ if parsed_args.device_id is not None:
+ attrs['device_id'] = parsed_args.device_id
+ if parsed_args.device_owner is not None:
+ attrs['device_owner'] = parsed_args.device_owner
+ if parsed_args.admin_state is not None:
+ attrs['admin_state_up'] = parsed_args.admin_state
+ if parsed_args.binding_profile is not None:
+ attrs['binding:profile'] = parsed_args.binding_profile
+ if parsed_args.vnic_type is not None:
+ attrs['binding:vnic_type'] = parsed_args.vnic_type
+ if parsed_args.host_id is not None:
+ attrs['binding:host_id'] = parsed_args.host_id
+
+ # The remaining options do not support 'port set' command, so they require
+ # additional check
+ if 'mac_address' in parsed_args and parsed_args.mac_address is not None:
+ attrs['mac_address'] = parsed_args.mac_address
+ if 'network' in parsed_args and parsed_args.network is not None:
+ attrs['network_id'] = parsed_args.network
+ if 'project' in parsed_args and parsed_args.project is not None:
+ # TODO(singhj): since 'project' logic is common among
+ # router, network, port etc., maybe move it to a common file.
+ identity_client = client_manager.identity
+ project_id = identity_common.find_project(
+ identity_client,
+ parsed_args.project,
+ parsed_args.project_domain,
+ ).id
+ attrs['tenant_id'] = project_id
+
+ return attrs
+
+
+def _prepare_fixed_ips(client_manager, parsed_args):
+ """Fix and properly format fixed_ip option.
+
+ Appropriately convert any subnet names to their respective ids.
+ Convert fixed_ips in parsed args to be in valid dictionary format:
+ {'subnet': 'foo'}.
+ """
+ client = client_manager.network
+ ips = []
+
+ if parsed_args.fixed_ip:
+ for ip_spec in parsed_args.fixed_ip:
+ if 'subnet' in ip_spec:
+ subnet_name_id = ip_spec['subnet']
+ if subnet_name_id:
+ _subnet = client.find_subnet(subnet_name_id,
+ ignore_missing=False)
+ ip_spec['subnet_id'] = _subnet.id
+ del ip_spec['subnet']
+
+ if 'ip-address' in ip_spec:
+ ip_spec['ip_address'] = ip_spec['ip-address']
+ del ip_spec['ip-address']
+
+ ips.append(ip_spec)
+
+ if ips:
+ parsed_args.fixed_ip = ips
+
+
+def _add_updatable_args(parser):
+ parser.add_argument(
+ '--fixed-ip',
+ metavar='subnet=<subnet>,ip-address=<ip-address>',
+ action=parseractions.MultiKeyValueAction,
+ optional_keys=['subnet', 'ip-address'],
+ help='Desired IP and/or subnet (name or ID) for this port: '
+ 'subnet=<subnet>,ip-address=<ip-address> '
+ '(this option can be repeated)')
+ parser.add_argument(
+ '--device-id',
+ metavar='<device-id>',
+ help='Device ID of this port')
+ parser.add_argument(
+ '--device-owner',
+ metavar='<device-owner>',
+ help='Device owner of this port')
+ parser.add_argument(
+ '--vnic-type',
+ metavar='<vnic-type>',
+ choices=['direct', 'direct-physical', 'macvtap',
+ 'normal', 'baremetal'],
+ help='VNIC type for this port (direct | direct-physical |'
+ ' macvtap | normal(default) | baremetal)')
+ parser.add_argument(
+ '--binding-profile',
+ metavar='<binding-profile>',
+ action=parseractions.KeyValueAction,
+ help='Custom data to be passed as binding:profile: <key>=<value> '
+ '(this option can be repeated)')
+ parser.add_argument(
+ '--host-id',
+ metavar='<host-id>',
+ help='The ID of the host where the port is allocated'
+ )
+
+
+class CreatePort(command.ShowOne):
+ """Create a new port"""
+
+ def get_parser(self, prog_name):
+ parser = super(CreatePort, self).get_parser(prog_name)
+
+ parser.add_argument(
+ '--network',
+ metavar='<network>',
+ required=True,
+ help='Network this port belongs to (name or ID)')
+ _add_updatable_args(parser)
+ admin_group = parser.add_mutually_exclusive_group()
+ admin_group.add_argument(
+ '--enable',
+ dest='admin_state',
+ action='store_true',
+ default=True,
+ help='Enable port (default)',
+ )
+ admin_group.add_argument(
+ '--disable',
+ dest='admin_state',
+ action='store_false',
+ help='Disable port',
+ )
+ parser.add_argument(
+ '--mac-address',
+ metavar='<mac-address>',
+ help='MAC address of this port')
+ parser.add_argument(
+ '--project',
+ metavar='<project>',
+ help="Owner's project (name or ID)")
+ parser.add_argument(
+ 'name',
+ metavar='<name>',
+ help='Name of this port')
+ identity_common.add_project_domain_option_to_parser(parser)
+ # TODO(singhj): Add support for extended options:
+ # qos,security groups,dhcp, address pairs
+ return parser
+
+ def take_action(self, parsed_args):
+ client = self.app.client_manager.network
+ _network = client.find_network(parsed_args.network,
+ ignore_missing=False)
+ parsed_args.network = _network.id
+ _prepare_fixed_ips(self.app.client_manager, parsed_args)
+ attrs = _get_attrs(self.app.client_manager, parsed_args)
+ obj = client.create_port(**attrs)
+ columns = _get_columns(obj)
+ data = utils.get_item_properties(obj, columns, formatters=_formatters)
+
+ return columns, data
class DeletePort(command.Command):
@@ -90,4 +255,4 @@ class ShowPort(command.ShowOne):
obj = client.find_port(parsed_args.port, ignore_missing=False)
columns = _get_columns(obj)
data = utils.get_item_properties(obj, columns, formatters=_formatters)
- return (tuple(columns), data)
+ return columns, data