diff options
author | Sahina Bose <sabose@redhat.com> | 2014-04-21 13:57:07 +0530 |
---|---|---|
committer | Bala.FA <barumuga@redhat.com> | 2014-04-28 16:20:46 +0530 |
commit | b0688de9a2c282763275a47d85fc17b31b5c9848 (patch) | |
tree | 4f6e9a945889dd0530eac788ca4f5d2f11e075d5 | |
parent | a8a9f59b7c45f1ddc6692ac94ed13ec303484366 (diff) |
glustercli: Added method for split-brain status
Added method to check "volume heal <vol-name> info"
Change-Id: I367eee5c63e3256f8834ea3845ed7ada6b073001
Signed-off-by: Sahina Bose <sabose@redhat.com>
-rwxr-xr-x | glusternagios/glustercli.py | 50 | ||||
-rw-r--r-- | tests/test_glustercli.py | 50 |
2 files changed, 100 insertions, 0 deletions
diff --git a/glusternagios/glustercli.py b/glusternagios/glustercli.py index ff4781b..771feeb 100755 --- a/glusternagios/glustercli.py +++ b/glusternagios/glustercli.py @@ -88,6 +88,12 @@ class VolumeQuotaStatus: EXCEEDED = 'EXCEEDED' +class VolumeSplitBrainStatus: + NOTAPPLICABLE = 'NA' + OK = 'OK' + SPLITBRAIN = 'SPLITBRAIN' + + class TransportType: TCP = 'TCP' RDMA = 'RDMA' @@ -447,6 +453,50 @@ def _parseVolumeQuotaStatus(out): return VolumeQuotaStatus.OK +def _parseVolumeSelfHealSplitBrainInfo(out): + value = {} + splitbrainentries = 0 + for line in out: + if line.startswith('Number of entries:'): + entries = int(line.split(':')[1]) + if entries > 0: + splitbrainentries += entries + if splitbrainentries > 0: + value['status'] = VolumeSplitBrainStatus.SPLITBRAIN + else: + value['status'] = VolumeSplitBrainStatus.OK + value['unsyncedentries'] = splitbrainentries + return value + + +def volumeHealSplitBrainStatus(volumeName, remoteServer=None): + """ + Arguments: + * VolumeName + Returns: + {VOLUMENAME: {'status': SELFHEALSTATUS, + 'unsyncedentries': ENTRYCOUNT}} + """ + command = _getGlusterVolCmd() + ["heal", volumeName, "info"] + if remoteServer: + command += ['--remote-host=%s' % remoteServer] + + rc, out, err = _execGluster(command) + volume = {} + value = {} + if rc == 0: + value = _parseVolumeSelfHealSplitBrainInfo(out) + volume[volumeName] = value + return volume + else: + if len(err) > 0 and err[0].find("is not of type replicate") > -1: + value['status'] = VolumeSplitBrainStatus.NOTAPPLICABLE + value['unsyncedentries'] = 0 + volume[volumeName] = value + return volume + raise GlusterCmdFailedException(rc=rc, err=err) + + def volumeQuotaStatus(volumeName, remoteServer=None): """ Returns: diff --git a/tests/test_glustercli.py b/tests/test_glustercli.py index 526aa6e..1d7d517 100644 --- a/tests/test_glustercli.py +++ b/tests/test_glustercli.py @@ -1096,6 +1096,35 @@ class GlusterCliTests(TestCaseBase): except gcli.GlusterCmdFailedException: assert True + @mock.patch('glusternagios.utils.execCmd') + @mock.patch('glusternagios.glustercli._getGlusterVolCmd') + def test_getVolumeHealSplitBrainStatusNonRepl(self, mock_glusterVolCmd, + mock_execCmd,): + mock_glusterVolCmd.return_value = ["gluster", "volume"] + mock_execCmd.return_value = 2, None, ["Volume test-vol is not " + "of type replicate"] + expectedOut = {'test-vol': + {'status': gcli.VolumeSplitBrainStatus.NOTAPPLICABLE, + 'unsyncedentries': 0}} + status = gcli.volumeHealSplitBrainStatus("test-vol") + print(status) + self.assertEquals(status, expectedOut) + + @mock.patch('glusternagios.utils.execCmd') + @mock.patch('glusternagios.glustercli._getGlusterVolCmd') + def test_getVolumeHealSplitBrainStatus(self, mock_glusterVolCmd, + mock_execCmd,): + mock_glusterVolCmd.return_value = ["gluster", "volume"] + mock_execCmd.return_value = (0, + self.__getGlusterSelfHealInfoResult(), + None) + expectedOut = {'test-vol': + {'status': gcli.VolumeSplitBrainStatus.SPLITBRAIN, + 'unsyncedentries': 10}} + status = gcli.volumeHealSplitBrainStatus("test-vol") + print(status) + self.assertEquals(status, expectedOut) + def __getQuotaOut(self): return \ [" Path Hard-limit Soft-limit" @@ -1106,3 +1135,24 @@ class GlusterCliTests(TestCaseBase): " 200.0KB 0Bytes No No", "/test/rewe 200.0KB 80% " "200.0KB 0Bytes Yes Yes"] + + def __getGlusterSelfHealInfoResult(self): + return ["Gathering list of entries to be healed " + "on volume rep has been successful", + "", + "Brick node2:/bricks/b3", + "Status: Brick is Not connected", + "Number of entries: 0" + "", + "Brick node1:/bricks/b3", + "Number of entries: 10", + "/dir.7/file.5", + "/dir.8/file.3", + "/dir.9/file.5", + "/dir.2/file.4", + "/dir.9/file.4", + "/dir.4/file.1", + "/file.4", + "/dir.7/file.2", + "/dir.10/file.2", + "/dir.7/file.4"] |