From f11d1bb7cc73bc8a8a149a2967616ae7c1ea9500 Mon Sep 17 00:00:00 2001
From: zhanggang <zhanggang@cmss.chinamobile.com>
Date: Tue, 26 Dec 2017 04:08:01 -0500
Subject: [PATCH] Add reset-status to OSC

This change adds database support to the python-openstackclient
project for the cluster-reset-status and reset-status command.

The trove command cluster-reset-status is now:
    openstack database cluster reset status
The trove command reset-status is now:
    openstack database instance reset status

Change-Id: I8945327d244bfd2a9afe7febb7179467a8be9bd0
Partially-Implements: blueprint trove-support-in-python-openstackclient
---
 ...-reset-status-to-osc-bd84dcdc369e2270.yaml | 10 ++++++++
 setup.cfg                                     |  2 ++
 troveclient/osc/v1/database_clusters.py       | 20 ++++++++++++++++
 troveclient/osc/v1/database_instances.py      | 23 +++++++++++++++++++
 .../tests/osc/v1/test_database_clusters.py    | 16 +++++++++++++
 .../tests/osc/v1/test_database_instances.py   | 17 ++++++++++++++
 6 files changed, 88 insertions(+)
 create mode 100644 releasenotes/notes/add-reset-status-to-osc-bd84dcdc369e2270.yaml

diff --git a/releasenotes/notes/add-reset-status-to-osc-bd84dcdc369e2270.yaml b/releasenotes/notes/add-reset-status-to-osc-bd84dcdc369e2270.yaml
new file mode 100644
index 00000000..aa10754e
--- /dev/null
+++ b/releasenotes/notes/add-reset-status-to-osc-bd84dcdc369e2270.yaml
@@ -0,0 +1,10 @@
+---
+features:
+  - |
+    The command ``trove reset-status`` is now available
+    to use in the python-openstackclient CLI as ``openstack database
+    instance reset status``
+    The command ``trove cluster-reset-status`` is now available
+    to use in the python-openstackclient CLI as ``openstack database
+    cluster reset status``
+
diff --git a/setup.cfg b/setup.cfg
index e6185a32..138d230e 100644
--- a/setup.cfg
+++ b/setup.cfg
@@ -38,6 +38,7 @@ openstack.database.v1 =
     database_cluster_create = troveclient.osc.v1.database_clusters:CreateDatabaseCluster
     database_cluster_delete = troveclient.osc.v1.database_clusters:DeleteDatabaseCluster
     database_cluster_list = troveclient.osc.v1.database_clusters:ListDatabaseClusters
+    database_cluster_reset_status = troveclient.osc.v1.database_clusters:ResetDatabaseClusterStatus
     database_cluster_show = troveclient.osc.v1.database_clusters:ShowDatabaseCluster
     database_configuration_create = troveclient.osc.v1.database_configurations:CreateDatabaseConfiguration
     database_configuration_delete = troveclient.osc.v1.database_configurations:DeleteDatabaseConfiguration
@@ -53,6 +54,7 @@ openstack.database.v1 =
     database_instance_create = troveclient.osc.v1.database_instances:CreateDatabaseInstance
     database_instance_delete = troveclient.osc.v1.database_instances:DeleteDatabaseInstance
     database_instance_list = troveclient.osc.v1.database_instances:ListDatabaseInstances
+    database_instance_reset_status = troveclient.osc.v1.database_instances:ResetDatabaseInstanceStatus
     database_instance_show = troveclient.osc.v1.database_instances:ShowDatabaseInstance
     database_limit_list = troveclient.osc.v1.database_limits:ListDatabaseLimits
     database_user_create = troveclient.osc.v1.database_users:CreateDatabaseUser
diff --git a/troveclient/osc/v1/database_clusters.py b/troveclient/osc/v1/database_clusters.py
index 459794e8..f4723313 100644
--- a/troveclient/osc/v1/database_clusters.py
+++ b/troveclient/osc/v1/database_clusters.py
@@ -185,3 +185,23 @@ class CreateDatabaseCluster(command.ShowOne):
                                            locality=parsed_args.locality)
         cluster = set_attributes_for_print_detail(cluster)
         return zip(*sorted(six.iteritems(cluster)))
+
+
+class ResetDatabaseClusterStatus(command.Command):
+
+    _description = _("Set the cluster task to NONE.")
+
+    def get_parser(self, prog_name):
+        parser = super(ResetDatabaseClusterStatus, self).get_parser(prog_name)
+        parser.add_argument(
+            'cluster',
+            metavar='<cluster>',
+            help=_('ID or name of the cluster.'),
+        )
+        return parser
+
+    def take_action(self, parsed_args):
+        database_clusters = self.app.client_manager.database.clusters
+        cluster = utils.find_resource(database_clusters,
+                                      parsed_args.cluster)
+        database_clusters.reset_status(cluster)
diff --git a/troveclient/osc/v1/database_instances.py b/troveclient/osc/v1/database_instances.py
index 0c362019..604e63b4 100644
--- a/troveclient/osc/v1/database_instances.py
+++ b/troveclient/osc/v1/database_instances.py
@@ -364,3 +364,26 @@ class CreateDatabaseInstance(command.ShowOne):
                                        region_name=parsed_args.region)
         instance = set_attributes_for_print_detail(instance)
         return zip(*sorted(six.iteritems(instance)))
+
+
+class ResetDatabaseInstanceStatus(command.Command):
+
+    _description = _("Set the task status of an instance to NONE if the "
+                     "instance is in BUILD or ERROR state. Resetting task "
+                     "status of an instance in BUILD state will allow "
+                     "the instance to be deleted.")
+
+    def get_parser(self, prog_name):
+        parser = super(ResetDatabaseInstanceStatus, self).get_parser(prog_name)
+        parser.add_argument(
+            'instance',
+            metavar='<instance>',
+            help=_('ID or name of the instance'),
+        )
+        return parser
+
+    def take_action(self, parsed_args):
+        db_instances = self.app.client_manager.database.instances
+        instance = osc_utils.find_resource(db_instances,
+                                           parsed_args.instance)
+        db_instances.reset_status(instance)
diff --git a/troveclient/tests/osc/v1/test_database_clusters.py b/troveclient/tests/osc/v1/test_database_clusters.py
index 9c32ed9b..751b8478 100644
--- a/troveclient/tests/osc/v1/test_database_clusters.py
+++ b/troveclient/tests/osc/v1/test_database_clusters.py
@@ -150,3 +150,19 @@ class TestDatabaseClusterCreate(TestClusters):
         columns, data = self.cmd.take_action(parsed_args)
         self.assertEqual(self.columns, columns)
         self.assertEqual(self.values, data)
+
+
+class TestDatabaseClusterResetStatus(TestClusters):
+
+    def setUp(self):
+        super(TestDatabaseClusterResetStatus, self).setUp()
+        self.cmd = database_clusters.ResetDatabaseClusterStatus(self.app, None)
+
+    @mock.patch.object(utils, 'find_resource')
+    def test_cluster_reset_status(self, mock_find):
+        args = ['cluster1']
+        mock_find.return_value = args[0]
+        parsed_args = self.check_parser(self.cmd, args, [])
+        result = self.cmd.take_action(parsed_args)
+        self.cluster_client.reset_status.assert_called_with('cluster1')
+        self.assertIsNone(result)
diff --git a/troveclient/tests/osc/v1/test_database_instances.py b/troveclient/tests/osc/v1/test_database_instances.py
index 9cf09f90..39b475ea 100644
--- a/troveclient/tests/osc/v1/test_database_instances.py
+++ b/troveclient/tests/osc/v1/test_database_instances.py
@@ -166,3 +166,20 @@ class TestDatabaseInstanceCreate(TestInstances):
         columns, data = self.cmd.take_action(parsed_args)
         self.assertEqual(self.columns, columns)
         self.assertEqual(self.values, data)
+
+
+class TestDatabaseInstanceResetStatus(TestInstances):
+
+    def setUp(self):
+        super(TestDatabaseInstanceResetStatus, self).setUp()
+        self.cmd = database_instances.ResetDatabaseInstanceStatus(self.app,
+                                                                  None)
+
+    @mock.patch.object(utils, 'find_resource')
+    def test_instance_reset_status(self, mock_find):
+        args = ['instance1']
+        mock_find.return_value = args[0]
+        parsed_args = self.check_parser(self.cmd, args, [])
+        result = self.cmd.take_action(parsed_args)
+        self.instance_client.reset_status.assert_called_with('instance1')
+        self.assertIsNone(result)