Merge "Support node-adopt/preview CLI"
This commit is contained in:
commit
5776a9c5c3
@ -27,7 +27,7 @@ def create_connection(prof=None, user_agent=None, **kwargs):
|
|||||||
if region_name:
|
if region_name:
|
||||||
prof.set_region('clustering', region_name)
|
prof.set_region('clustering', region_name)
|
||||||
|
|
||||||
prof.set_api_version('clustering', '1.5')
|
prof.set_api_version('clustering', '1.7')
|
||||||
try:
|
try:
|
||||||
conn = connection.Connection(profile=prof, user_agent=user_agent,
|
conn = connection.Connection(profile=prof, user_agent=user_agent,
|
||||||
**kwargs)
|
**kwargs)
|
||||||
|
@ -225,6 +225,22 @@ def format_parameters(params, parse_semicolon=True):
|
|||||||
return parameters
|
return parameters
|
||||||
|
|
||||||
|
|
||||||
|
def format_json_parameter(param):
|
||||||
|
'''Return JSON dict from JSON formatted param.
|
||||||
|
|
||||||
|
:parameter param JSON formatted string
|
||||||
|
:return JSON dict
|
||||||
|
'''
|
||||||
|
if not param:
|
||||||
|
return {}
|
||||||
|
|
||||||
|
try:
|
||||||
|
return jsonutils.loads(param)
|
||||||
|
except ValueError:
|
||||||
|
msg = _('Malformed parameter(%s). Use the JSON format.') % param
|
||||||
|
raise exc.CommandError(msg)
|
||||||
|
|
||||||
|
|
||||||
def get_spec_content(filename):
|
def get_spec_content(filename):
|
||||||
with open(filename, 'r') as f:
|
with open(filename, 'r') as f:
|
||||||
try:
|
try:
|
||||||
|
@ -23,7 +23,7 @@ LOG = logging.getLogger(__name__)
|
|||||||
DEFAULT_CLUSTERING_API_VERSION = '1'
|
DEFAULT_CLUSTERING_API_VERSION = '1'
|
||||||
API_VERSION_OPTION = 'os_clustering_api_version'
|
API_VERSION_OPTION = 'os_clustering_api_version'
|
||||||
API_NAME = 'clustering'
|
API_NAME = 'clustering'
|
||||||
CURRENT_API_VERSION = '1.5'
|
CURRENT_API_VERSION = '1.7'
|
||||||
|
|
||||||
|
|
||||||
def make_client(instance):
|
def make_client(instance):
|
||||||
|
@ -458,6 +458,158 @@ class TestNodeRecover(TestNode):
|
|||||||
self.assertIn('Node not found: node1', str(error))
|
self.assertIn('Node not found: node1', str(error))
|
||||||
|
|
||||||
|
|
||||||
|
class TestNodeAdopt(TestNode):
|
||||||
|
defaults = {
|
||||||
|
"identity": "fake-resource-id",
|
||||||
|
"metadata": {},
|
||||||
|
"name": "my_node",
|
||||||
|
"overrides": {},
|
||||||
|
"role": None,
|
||||||
|
"snapshot": False,
|
||||||
|
"type": "os.nova.server-1.0"
|
||||||
|
}
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
super(TestNodeAdopt, self).setUp()
|
||||||
|
self.cmd = osc_node.AdoptNode(self.app, None)
|
||||||
|
fake_node = mock.Mock(
|
||||||
|
action="2366d440-c73e-4961-9254-6d1c3af7c167",
|
||||||
|
cluster_id="",
|
||||||
|
created_at=None,
|
||||||
|
data={},
|
||||||
|
domain=None,
|
||||||
|
id="0df0931b-e251-4f2e-8719-4ebfda3627ba",
|
||||||
|
index=-1,
|
||||||
|
init_time="2015-03-05T08:53:15",
|
||||||
|
metadata={},
|
||||||
|
physical_id=None,
|
||||||
|
profile_id="edc63d0a-2ca4-48fa-9854-27926da76a4a",
|
||||||
|
profile_name="mystack",
|
||||||
|
project_id="6e18cc2bdbeb48a5b3cad2dc499f6804",
|
||||||
|
role="master",
|
||||||
|
status="INIT",
|
||||||
|
status_reason="Initializing",
|
||||||
|
updated_at=None,
|
||||||
|
user_id="5e5bf8027826429c96af157f68dc9072"
|
||||||
|
)
|
||||||
|
fake_node.name = "my_node"
|
||||||
|
fake_node.to_dict = mock.Mock(return_value={})
|
||||||
|
|
||||||
|
self.mock_client.adopt_node = mock.Mock(return_value=fake_node)
|
||||||
|
self.mock_client.get_node = mock.Mock(return_value=fake_node)
|
||||||
|
|
||||||
|
def test_node_adopt_defaults(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--name', 'my_node']
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(False, **self.defaults)
|
||||||
|
|
||||||
|
def test_node_adopt_with_metadata(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--metadata', 'key1=value1;key2=value2',
|
||||||
|
'--name', 'my_node']
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['metadata'] = {'key1': 'value1', 'key2': 'value2'}
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(False, **kwargs)
|
||||||
|
|
||||||
|
def test_node_adopt_with_override(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--overrides',
|
||||||
|
'{"networks": [{"network": "fake-net-name"}]}',
|
||||||
|
'--name', 'my_node']
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['overrides'] = {'networks': [{'network': 'fake-net-name'}]}
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(False, **kwargs)
|
||||||
|
|
||||||
|
def test_node_adopt_with_role(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--role', 'master',
|
||||||
|
'--name', 'my_node']
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['role'] = 'master'
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(False, **kwargs)
|
||||||
|
|
||||||
|
def test_node_adopt_with_snapshot(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--snapshot',
|
||||||
|
'--name', 'my_node']
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['snapshot'] = True
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(False, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
class TestNodeAdoptPreview(TestNode):
|
||||||
|
defaults = {
|
||||||
|
"identity": "fake-resource-id",
|
||||||
|
"overrides": {},
|
||||||
|
"snapshot": False,
|
||||||
|
"type": "os.nova.server-1.0"
|
||||||
|
}
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
super(TestNodeAdoptPreview, self).setUp()
|
||||||
|
self.cmd = osc_node.AdoptNode(self.app, None)
|
||||||
|
self.fake_node_preview = {
|
||||||
|
"node_profile": {
|
||||||
|
"node_preview": {
|
||||||
|
"properties": {
|
||||||
|
|
||||||
|
},
|
||||||
|
"type": "os.nova.server",
|
||||||
|
"version": "1.0"}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
self.mock_client.adopt_node = mock.Mock(
|
||||||
|
return_value=self.fake_node_preview)
|
||||||
|
self.mock_client.get_node = mock.Mock(
|
||||||
|
return_value=self.fake_node_preview)
|
||||||
|
|
||||||
|
def test_node_adopt_preview_default(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--preview']
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(True, **self.defaults)
|
||||||
|
|
||||||
|
def test_node_adopt_preview_with_overrides(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--overrides',
|
||||||
|
'{"networks": [{"network": "fake-net-name"}]}',
|
||||||
|
'--preview']
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['overrides'] = {'networks': [{'network': 'fake-net-name'}]}
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(True, **kwargs)
|
||||||
|
|
||||||
|
def test_node_adopt_preview_with_snapshot(self):
|
||||||
|
arglist = ['--identity', 'fake-resource-id',
|
||||||
|
'--type', 'os.nova.server-1.0',
|
||||||
|
'--snapshot', '--preview']
|
||||||
|
parsed_args = self.check_parser(self.cmd, arglist, [])
|
||||||
|
kwargs = copy.deepcopy(self.defaults)
|
||||||
|
kwargs['snapshot'] = True
|
||||||
|
self.cmd.take_action(parsed_args)
|
||||||
|
self.mock_client.adopt_node.assert_called_with(True, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
class TestNodeOp(TestNode):
|
class TestNodeOp(TestNode):
|
||||||
|
|
||||||
response = {"action": "1db0f5c5-9183-4c47-9ef1-a5a97402a2c1"}
|
response = {"action": "1db0f5c5-9183-4c47-9ef1-a5a97402a2c1"}
|
||||||
|
@ -1561,6 +1561,76 @@ class ShellTest(testtools.TestCase):
|
|||||||
service.create_node.assert_called_once_with(**attrs)
|
service.create_node.assert_called_once_with(**attrs)
|
||||||
mock_show.assert_called_once_with(service, 'node_id')
|
mock_show.assert_called_once_with(service, 'node_id')
|
||||||
|
|
||||||
|
@mock.patch.object(sh, '_show_node')
|
||||||
|
def test_do_node_adopt(self, mock_show):
|
||||||
|
args = {
|
||||||
|
'identity': 'fake-resoruce-id',
|
||||||
|
'name': 'adopt-node1',
|
||||||
|
'role': 'master',
|
||||||
|
'metadata': ['user=demo'],
|
||||||
|
'snapshot': None,
|
||||||
|
'overrides': '{"networks": [{"network": "fake-net-name"}]}',
|
||||||
|
'type': 'os.nova.server-1.0',
|
||||||
|
'preview': False
|
||||||
|
}
|
||||||
|
args = self._make_args(args)
|
||||||
|
attrs = {
|
||||||
|
'identity': 'fake-resoruce-id',
|
||||||
|
'name': 'adopt-node1',
|
||||||
|
'role': 'master',
|
||||||
|
'metadata': {'user': 'demo'},
|
||||||
|
'overrides': {'networks': [{'network': 'fake-net-name'}]},
|
||||||
|
'snapshot': None,
|
||||||
|
'type': 'os.nova.server-1.0',
|
||||||
|
}
|
||||||
|
service = mock.Mock()
|
||||||
|
node = mock.Mock()
|
||||||
|
node.id = 'node_id'
|
||||||
|
service.adopt_node.return_value = node
|
||||||
|
sh.do_node_adopt(service, args)
|
||||||
|
service.adopt_node.assert_called_once_with(**attrs)
|
||||||
|
mock_show.assert_called_once_with(service, 'node_id')
|
||||||
|
|
||||||
|
@mock.patch.object(utils, 'print_dict')
|
||||||
|
@mock.patch.object(utils, 'nested_dict_formatter')
|
||||||
|
def test_do_node_adopt_preview(self, mock_nest, mock_print):
|
||||||
|
args = {
|
||||||
|
'identity': 'fake-resoruce-id',
|
||||||
|
'snapshot': None,
|
||||||
|
'overrides': '{"networks": [{"network": "fake-net-name"}]}',
|
||||||
|
'type': 'os.nova.server-1.0',
|
||||||
|
'preview': True
|
||||||
|
}
|
||||||
|
args = self._make_args(args)
|
||||||
|
attrs = {
|
||||||
|
'identity': 'fake-resoruce-id',
|
||||||
|
'overrides': {'networks': [{'network': 'fake-net-name'}]},
|
||||||
|
'snapshot': None,
|
||||||
|
'type': 'os.nova.server-1.0',
|
||||||
|
}
|
||||||
|
|
||||||
|
fake_preview = {
|
||||||
|
"node_profile": {
|
||||||
|
"node_preview": {
|
||||||
|
"properties": {
|
||||||
|
},
|
||||||
|
"type": "os.nova.server",
|
||||||
|
"version": "1.0"}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
service = mock.Mock()
|
||||||
|
service.adopt_node.return_value = fake_preview
|
||||||
|
sh.do_node_adopt(service, args)
|
||||||
|
service.adopt_node.assert_called_once_with(True, **attrs)
|
||||||
|
|
||||||
|
formatters = {}
|
||||||
|
formatters['node_preview'] = utils.nested_dict_formatter(
|
||||||
|
['type', 'version', 'properties'],
|
||||||
|
['property', 'value'])
|
||||||
|
mock_print.assert_called_once_with(fake_preview['node_profile'],
|
||||||
|
formatters=formatters)
|
||||||
|
|
||||||
@mock.patch.object(sh, '_show_node')
|
@mock.patch.object(sh, '_show_node')
|
||||||
def test_do_node_show(self, mock_show):
|
def test_do_node_show(self, mock_show):
|
||||||
service = mock.Mock()
|
service = mock.Mock()
|
||||||
|
@ -346,6 +346,15 @@ class Client(object):
|
|||||||
"""
|
"""
|
||||||
return self.service.create_node(**attrs)
|
return self.service.create_node(**attrs)
|
||||||
|
|
||||||
|
def adopt_node(self, preview=False, **attrs):
|
||||||
|
"""Adopt a node
|
||||||
|
|
||||||
|
Doc link:
|
||||||
|
https://developer.openstack.org/api-ref/clustering/#adopt-node
|
||||||
|
https://developer.openstack.org/api-ref/clustering/#adopt-node-preview
|
||||||
|
"""
|
||||||
|
return self.service.adopt_node(preview, **attrs)
|
||||||
|
|
||||||
def get_node(self, node, details=False):
|
def get_node(self, node, details=False):
|
||||||
"""Show node details
|
"""Show node details
|
||||||
|
|
||||||
|
@ -163,6 +163,7 @@ def _show_node(senlin_client, node_id, show_details=False):
|
|||||||
if show_details and data['details']:
|
if show_details and data['details']:
|
||||||
formatters['details'] = senlin_utils.nested_dict_formatter(
|
formatters['details'] = senlin_utils.nested_dict_formatter(
|
||||||
list(data['details'].keys()), ['property', 'value'])
|
list(data['details'].keys()), ['property', 'value'])
|
||||||
|
|
||||||
columns = sorted(data.keys())
|
columns = sorted(data.keys())
|
||||||
return columns, utils.get_dict_properties(data, columns,
|
return columns, utils.get_dict_properties(data, columns,
|
||||||
formatters=formatters)
|
formatters=formatters)
|
||||||
@ -398,6 +399,102 @@ class RecoverNode(command.Command):
|
|||||||
% {'nid': nid, 'action': resp['action']})
|
% {'nid': nid, 'action': resp['action']})
|
||||||
|
|
||||||
|
|
||||||
|
class AdoptNode(command.ShowOne):
|
||||||
|
"""Adopt (or preview) the node."""
|
||||||
|
|
||||||
|
log = logging.getLogger(__name__ + ".AdoptNode")
|
||||||
|
|
||||||
|
def get_parser(self, prog_name):
|
||||||
|
parser = super(AdoptNode, self).get_parser(prog_name)
|
||||||
|
parser.add_argument(
|
||||||
|
'--identity',
|
||||||
|
metavar='<identity>',
|
||||||
|
required=True,
|
||||||
|
help=_('Physical resource id.'))
|
||||||
|
parser.add_argument(
|
||||||
|
'--type',
|
||||||
|
metavar='<type>',
|
||||||
|
required=True,
|
||||||
|
help=_('The name of the profile type.')
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--role',
|
||||||
|
metavar='<role>',
|
||||||
|
help=_('Role for this node in the specific cluster.')
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--metadata',
|
||||||
|
metavar='<"key1=value1;key2=value2...">',
|
||||||
|
help=_('Metadata values to be attached to the node. '
|
||||||
|
'This can be specified multiple times, or once with '
|
||||||
|
'key-value pairs separated by a semicolon.'),
|
||||||
|
action='append'
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--name',
|
||||||
|
metavar='<node-name>',
|
||||||
|
help=_('Name of the node to adopt.')
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--overrides',
|
||||||
|
metavar='<json>',
|
||||||
|
help=_('JSON formatted specification for overriding this node '
|
||||||
|
'properties.')
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--preview',
|
||||||
|
default=False,
|
||||||
|
help=_('Whether preview the node adopt request. If set, '
|
||||||
|
'only previewing this node and do not adopt.'),
|
||||||
|
action='store_true',
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'--snapshot',
|
||||||
|
default=False,
|
||||||
|
help=_('Whether a shapshot of the existing physical object '
|
||||||
|
'should be created before the object is adopted as '
|
||||||
|
'a node.'),
|
||||||
|
action='store_true'
|
||||||
|
)
|
||||||
|
return parser
|
||||||
|
|
||||||
|
def take_action(self, parsed_args):
|
||||||
|
self.log.debug("take_action(%s)", parsed_args)
|
||||||
|
|
||||||
|
senlin_client = self.app.client_manager.clustering
|
||||||
|
|
||||||
|
preview = True if parsed_args.preview else False
|
||||||
|
attrs = {
|
||||||
|
'identity': parsed_args.identity,
|
||||||
|
'overrides': senlin_utils.format_json_parameter(
|
||||||
|
parsed_args.overrides),
|
||||||
|
'snapshot': parsed_args.snapshot,
|
||||||
|
'type': parsed_args.type
|
||||||
|
}
|
||||||
|
|
||||||
|
if not preview:
|
||||||
|
attrs.update({
|
||||||
|
'name': parsed_args.name,
|
||||||
|
'role': parsed_args.role,
|
||||||
|
'metadata': senlin_utils.format_parameters(
|
||||||
|
parsed_args.metadata),
|
||||||
|
})
|
||||||
|
|
||||||
|
node = senlin_client.adopt_node(preview, **attrs)
|
||||||
|
|
||||||
|
if not preview:
|
||||||
|
return _show_node(senlin_client, node.id)
|
||||||
|
else:
|
||||||
|
formatters = {}
|
||||||
|
formatters['node_preview'] = senlin_utils.nested_dict_formatter(
|
||||||
|
['type', 'version', 'properties'],
|
||||||
|
['property', 'value'])
|
||||||
|
data = node['node_profile']
|
||||||
|
columns = sorted(data.keys())
|
||||||
|
return columns, utils.get_dict_properties(data, columns,
|
||||||
|
formatters=formatters)
|
||||||
|
|
||||||
|
|
||||||
class NodeOp(command.Lister):
|
class NodeOp(command.Lister):
|
||||||
"""Perform an operation on a node."""
|
"""Perform an operation on a node."""
|
||||||
log = logging.getLogger(__name__ + ".NodeOp")
|
log = logging.getLogger(__name__ + ".NodeOp")
|
||||||
|
@ -1329,6 +1329,71 @@ def do_node_create(service, args):
|
|||||||
_show_node(service, node.id)
|
_show_node(service, node.id)
|
||||||
|
|
||||||
|
|
||||||
|
@utils.arg('-i', '--identity', metavar='<IDENTITY>', required=True,
|
||||||
|
help=_('Physical resource id.'))
|
||||||
|
@utils.arg('-t', '--type', metavar='<TYPE>', required=True,
|
||||||
|
help=_('The name of the profile type.'))
|
||||||
|
@utils.arg('-r', '--role', metavar='<ROLE>',
|
||||||
|
help=_('Role for this node in the specific cluster.'))
|
||||||
|
@utils.arg('-M', '--metadata', metavar='<"KEY1=VALUE1;KEY2=VALUE2...">',
|
||||||
|
help=_('Metadata values to be attached to the node. '
|
||||||
|
'This can be specified multiple times, or once with '
|
||||||
|
'key-value pairs separated by a semicolon.'),
|
||||||
|
action='append')
|
||||||
|
@utils.arg('-n', '--name', metavar='<NAME>',
|
||||||
|
help=_('The name for the node.'))
|
||||||
|
@utils.arg('-o', '--overrides', metavar='<JSON">',
|
||||||
|
help=_('JSON formatted specification for overriding this node '
|
||||||
|
'properties.'))
|
||||||
|
@utils.arg('-p', '--preview', default=False,
|
||||||
|
help=_('Whether preview the node adopt request. If set, '
|
||||||
|
'only previewing this node and do not adopt.'),
|
||||||
|
action='store_true')
|
||||||
|
@utils.arg('-s', '--snapshot', default=False,
|
||||||
|
help=_('Whether a shapshot of the existing physical object should '
|
||||||
|
'be created before the object is adopted as a node.'),
|
||||||
|
action='store_true')
|
||||||
|
def do_node_adopt(service, args):
|
||||||
|
"""Adopt (or preview) a node."""
|
||||||
|
show_deprecated('senlin node-adopt', 'openstack cluster node adopt')
|
||||||
|
if args.preview:
|
||||||
|
_do_node_adopt_preview(service, args)
|
||||||
|
else:
|
||||||
|
_do_node_adopt(service, args)
|
||||||
|
|
||||||
|
|
||||||
|
def _do_node_adopt_preview(service, args):
|
||||||
|
attrs = {
|
||||||
|
'identity': args.identity,
|
||||||
|
'overrides': utils.format_json_parameter(args.overrides),
|
||||||
|
'snapshot': args.snapshot,
|
||||||
|
'type': args.type
|
||||||
|
}
|
||||||
|
|
||||||
|
node = service.adopt_node(True, **attrs)
|
||||||
|
|
||||||
|
formatters = {}
|
||||||
|
formatters['node_preview'] = utils.nested_dict_formatter(
|
||||||
|
['type', 'version', 'properties'],
|
||||||
|
['property', 'value'])
|
||||||
|
utils.print_dict(node['node_profile'], formatters=formatters)
|
||||||
|
|
||||||
|
|
||||||
|
def _do_node_adopt(service, args):
|
||||||
|
attrs = {
|
||||||
|
'identity': args.identity,
|
||||||
|
'name': args.name,
|
||||||
|
'role': args.role,
|
||||||
|
'metadata': utils.format_parameters(args.metadata),
|
||||||
|
'overrides': utils.format_json_parameter(args.overrides),
|
||||||
|
'snapshot': args.snapshot,
|
||||||
|
'type': args.type
|
||||||
|
}
|
||||||
|
|
||||||
|
node = service.adopt_node(**attrs)
|
||||||
|
_show_node(service, node.id)
|
||||||
|
|
||||||
|
|
||||||
@utils.arg('-D', '--details', default=False, action="store_true",
|
@utils.arg('-D', '--details', default=False, action="store_true",
|
||||||
help=_('Include physical object details.'))
|
help=_('Include physical object details.'))
|
||||||
@utils.arg('id', metavar='<NODE>',
|
@utils.arg('id', metavar='<NODE>',
|
||||||
|
@ -43,6 +43,7 @@ openstack.clustering.v1 =
|
|||||||
cluster_members_add = senlinclient.v1.cluster:ClusterNodeAdd
|
cluster_members_add = senlinclient.v1.cluster:ClusterNodeAdd
|
||||||
cluster_members_del = senlinclient.v1.cluster:ClusterNodeDel
|
cluster_members_del = senlinclient.v1.cluster:ClusterNodeDel
|
||||||
cluster_members_replace = senlinclient.v1.cluster:ClusterNodeReplace
|
cluster_members_replace = senlinclient.v1.cluster:ClusterNodeReplace
|
||||||
|
cluster_node_adopt = senlinclient.v1.node:AdoptNode
|
||||||
cluster_node_check = senlinclient.v1.node:CheckNode
|
cluster_node_check = senlinclient.v1.node:CheckNode
|
||||||
cluster_node_create = senlinclient.v1.node:CreateNode
|
cluster_node_create = senlinclient.v1.node:CreateNode
|
||||||
cluster_node_delete = senlinclient.v1.node:DeleteNode
|
cluster_node_delete = senlinclient.v1.node:DeleteNode
|
||||||
|
Loading…
x
Reference in New Issue
Block a user