Skip to content

Commit

Permalink
Solve issue with non RAID 5 and add CI
Browse files Browse the repository at this point in the history
  • Loading branch information
nicolargo committed Jan 28, 2023
1 parent 97fd471 commit 435a828
Show file tree
Hide file tree
Showing 3 changed files with 72 additions and 12 deletions.
52 changes: 43 additions & 9 deletions pymdstat/pymdstat.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,23 +37,30 @@ def get_stats(self):
return self.stats

def personalities(self):
"""Return the personalities (list)."""
"""Return the personalities (list).
List of all the software RAID levels supported by your md driver
"""
return self.get_stats()['personalities']

def arrays(self):
"""Return the arrays (list)."""
"""Return the arrays (list).
List of actual RAID arrays configured on your system
"""
return self.get_stats()['arrays'].keys()

def type(self, array):
"""Return the array's type."""
return self.get_stats()['arrays'][array]['type']

def status(self, array):
"""Return the array's status."""
"""Return the array's status.
Status of the array (active, inactive, ...)."""
return self.get_stats()['arrays'][array]['status']

def components(self, array):
"""Return the components of the arrays (list)."""
"""Return the components of the arrays (list).
List of devices that belong to that array.
"""
return self.get_stats()['arrays'][array]['components'].keys()

def available(self, array):
Expand Down Expand Up @@ -119,6 +126,11 @@ def get_arrays(self, lines, personalities=[]):
# md config/status line
i += 1
ret[md_device].update(self.get_md_status(lines[i]))
# action line
if ret[md_device].get('config') and '_' in ret[md_device].get('config'):
i += 1
print(lines[i])
ret[md_device].update(self.get_md_action(lines[i]))
i += 1

return ret
Expand Down Expand Up @@ -150,18 +162,40 @@ def get_md_status(self, line):
ret = {}

splitted = split('\W+', line)
if len(splitted) < 7:
ret['available'] = None
ret['used'] = None
ret['config'] = None
else:
if line.rstrip().endswith(']'):
# The final 2 entries on this line: [n/m] [UUUU_]
# [n/m] means that ideally the array would have n devices however, currently, m devices are in use.
# Obviously when m >= n then things are good.
ret['available'] = splitted[-4]
ret['used'] = splitted[-3]
# [UUUU_] represents the status of each device, either U for up or _ for down.
ret['config'] = splitted[-2]
elif line.lstrip().startswith('['):
print(line)
pass
else:
ret['available'] = None
ret['used'] = None
ret['config'] = None

return ret

def get_md_action(self, line):
"""Return a dict of md action line.
@TODO:
Nothing is done for the moment, because i don't know if it is the only pattern.
But the following line should be analysed:
[>....................] reshape = 2.1% (115168/5237760) finish=3.7min speed=23033K/sec
and the output should be:
{'reshape': '2.1%', 'finish': '3.7min', 'speed': '23033K/sec'}
"""
ret = {}

splitted = split('\W+', line)
if line.lstrip().startswith('['):
pass

return ret

Expand Down
3 changes: 2 additions & 1 deletion tests/mdstat.03
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
Personalities : [raid6] [raid5] [raid4]
md0 : active raid5 sda1[0] sdd1[2] sdb1[1]
1465151808 blocks level 5, 64k chunk, algorithm 2 [4/3] [UUU_]
unused devices: <none>

unused devices: <none>
29 changes: 27 additions & 2 deletions unitest.py
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,33 @@ def test_009(self):
def test_010(self):
i = 10
mdstat_test = MdStat('./tests/mdstat.%s' % i)
# self.assertCountEqual(mdstat_test.get_stats()['personalities'], ['linear', 'multipath', 'raid0', 'raid1', 'raid6', 'raid5', 'raid4', 'raid10'])
# self.assertEqual(mdstat_test.get_stats()['arrays'], {'md2': {'status': 'inactive', 'available': None, 'used': None, 'components': {'sdb': '0'}, 'config': None, 'type': None}, 'md0': {'status': 'active', 'available': '2', 'used': '2', 'components': {'sde1': '0', 'sdf1': '1'}, 'config': 'UU', 'type': 'raid1'}, 'md1': {'status': 'active', 'available': '2', 'used': '2', 'components': {'sde2': '0', 'sdf2': '1'}, 'config': 'UU', 'type': 'raid1'}})
self.assertEqual(mdstat_test.get_stats()['arrays']['md126'], {'status': 'active', 'available': None, 'used': None, 'components': {'nvme0n1': '0', 'nvme1n1': '1'}, 'config': None, 'type': 'raid0'})
self.assertEqual(mdstat_test.get_stats()['arrays']['md129'], {'status': 'active', 'available': '2', 'used': '2', 'components': {'sda3': '0', 'sdd3': '1'}, 'config': 'UU', 'type': 'raid1'})

def test_011(self):
i = 11
mdstat_test = MdStat('./tests/mdstat.%s' % i)
self.assertEqual(type(mdstat_test.get_stats()), type({}))

def test_012(self):
i = 12
mdstat_test = MdStat('./tests/mdstat.%s' % i)
self.assertEqual(type(mdstat_test.get_stats()), type({}))

def test_013(self):
i = 13
mdstat_test = MdStat('./tests/mdstat.%s' % i)
self.assertEqual(type(mdstat_test.get_stats()), type({}))

def test_014(self):
i = 14
mdstat_test = MdStat('./tests/mdstat.%s' % i)
self.assertEqual(type(mdstat_test.get_stats()), type({}))

def test_015(self):
i = 15
mdstat_test = MdStat('./tests/mdstat.%s' % i)


if __name__ == '__main__':
unittest.main()

0 comments on commit 435a828

Please sign in to comment.