Allow rpc.MakeLegacyNodeInfo to parse non-LVM results
authorIustin Pop <iustin@google.com>
Fri, 1 Mar 2013 11:23:23 +0000 (12:23 +0100)
committerIustin Pop <iustin@google.com>
Mon, 4 Mar 2013 10:35:44 +0000 (11:35 +0100)
'MakeLegacyNodeInfo' is not the best place for this, but we'd have to
duplicate it if we wanted a LVM-less version, so the easiest is to add
an optional parameter that allows it to accept/skip LVM-less results.

It still requires at most one VG result, so its behaviour isn't
changed in this respect.

Signed-off-by: Iustin Pop <iustin@google.com>
Reviewed-by: Guido Trotter <ultrotter@google.com>

lib/rpc.py
test/py/ganeti.rpc_unittest.py

index 0c4bad0..f6da489 100644 (file)
@@ -1,7 +1,7 @@
 #
 #
 
-# Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Google Inc.
+# Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Google Inc.
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -571,18 +571,25 @@ def _EncodeBlockdevRename(value):
   return [(d.ToDict(), uid) for d, uid in value]
 
 
-def MakeLegacyNodeInfo(data):
+def MakeLegacyNodeInfo(data, require_vg_info=True):
   """Formats the data returned by L{rpc.RpcRunner.call_node_info}.
 
   Converts the data into a single dictionary. This is fine for most use cases,
   but some require information from more than one volume group or hypervisor.
 
+  @param require_vg_info: raise an error if the returnd vg_info
+      doesn't have any values
+
   """
-  (bootid, (vg_info, ), (hv_info, )) = data
+  (bootid, vgs_info, (hv_info, )) = data
+
+  ret = utils.JoinDisjointDicts(hv_info, {"bootid": bootid})
+
+  if require_vg_info or vgs_info:
+    (vg0_info, ) = vgs_info
+    ret = utils.JoinDisjointDicts(vg0_info, ret)
 
-  return utils.JoinDisjointDicts(utils.JoinDisjointDicts(vg_info, hv_info), {
-    "bootid": bootid,
-    })
+  return ret
 
 
 def _AnnotateDParamsDRBD(disk, (drbd_params, data_params, meta_params)):
index ace49af..7967173 100755 (executable)
@@ -1,7 +1,7 @@
 #!/usr/bin/python
 #
 
-# Copyright (C) 2010, 2011, 2012 Google Inc.
+# Copyright (C) 2010, 2011, 2012, 2013 Google Inc.
 #
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -889,5 +889,38 @@ class TestRpcRunner(unittest.TestCase):
                     msg="Configuration objects were modified")
 
 
+class TestLegacyNodeInfo(unittest.TestCase):
+  KEY_BOOT = "bootid"
+  KEY_VG = "disk_free"
+  KEY_HV = "cpu_count"
+  VAL_BOOT = 0
+  VAL_VG = 1
+  VAL_HV = 2
+  DICT_VG = {KEY_VG: VAL_VG}
+  DICT_HV = {KEY_HV: VAL_HV}
+  STD_LST = [VAL_BOOT, [DICT_VG], [DICT_HV]]
+  STD_DICT = {
+    KEY_BOOT: VAL_BOOT,
+    KEY_VG: VAL_VG,
+    KEY_HV: VAL_HV
+    }
+
+  def testStandard(self):
+    result = rpc.MakeLegacyNodeInfo(self.STD_LST)
+    self.assertEqual(result, self.STD_DICT)
+
+  def testReqVg(self):
+    my_lst = [self.VAL_BOOT, [], [self.DICT_HV]]
+    self.assertRaises(ValueError, rpc.MakeLegacyNodeInfo, my_lst)
+
+  def testNoReqVg(self):
+    my_lst = [self.VAL_BOOT, [], [self.DICT_HV]]
+    result = rpc.MakeLegacyNodeInfo(my_lst, require_vg_info = False)
+    self.assertEqual(result, {self.KEY_BOOT: self.VAL_BOOT,
+                              self.KEY_HV: self.VAL_HV})
+    result = rpc.MakeLegacyNodeInfo(self.STD_LST, require_vg_info = False)
+    self.assertEqual(result, self.STD_DICT)
+
+
 if __name__ == "__main__":
   testutils.GanetiTestProgram()