diff --git a/lib/utils.py b/lib/utils.py index 65ef2c3417110a67715bef98fc805ef304812653..f10bcec7d336c0e513e04c4d31f5d1e085306fd7 100644 --- a/lib/utils.py +++ b/lib/utils.py @@ -319,8 +319,17 @@ def RenameFile(old, new, mkdir=False, mkdir_mode=0750): # as efficient. if mkdir and err.errno == errno.ENOENT: # Create directory and try again - os.makedirs(os.path.dirname(new), mkdir_mode) + dirname = os.path.dirname(new) + try: + os.makedirs(dirname, mode=mkdir_mode) + except OSError, err: + # Ignore EEXIST. This is only handled in os.makedirs as included in + # Python 2.5 and above. + if err.errno != errno.EEXIST or not os.path.exists(dirname): + raise + return os.rename(old, new) + raise diff --git a/test/ganeti.utils_unittest.py b/test/ganeti.utils_unittest.py index 62f48051f103be8d6ad829e2dda675cb8b531867..fe7464de5d38ae62a60058867badbf382f946109 100755 --- a/test/ganeti.utils_unittest.py +++ b/test/ganeti.utils_unittest.py @@ -295,16 +295,27 @@ class TestRename(unittest.TestCase): def testSimpleRename1(self): """Simple rename 1""" utils.RenameFile(self.tmpfile, os.path.join(self.tmpdir, "xyz")) + self.assert_(os.path.isfile(os.path.join(self.tmpdir, "xyz"))) def testSimpleRename2(self): """Simple rename 2""" utils.RenameFile(self.tmpfile, os.path.join(self.tmpdir, "xyz"), mkdir=True) + self.assert_(os.path.isfile(os.path.join(self.tmpdir, "xyz"))) def testRenameMkdir(self): """Rename with mkdir""" utils.RenameFile(self.tmpfile, os.path.join(self.tmpdir, "test/xyz"), mkdir=True) + self.assert_(os.path.isdir(os.path.join(self.tmpdir, "test"))) + self.assert_(os.path.isfile(os.path.join(self.tmpdir, "test/xyz"))) + + utils.RenameFile(os.path.join(self.tmpdir, "test/xyz"), + os.path.join(self.tmpdir, "test/foo/bar/baz"), + mkdir=True) + self.assert_(os.path.isdir(os.path.join(self.tmpdir, "test"))) + self.assert_(os.path.isdir(os.path.join(self.tmpdir, "test/foo/bar"))) + self.assert_(os.path.isfile(os.path.join(self.tmpdir, "test/foo/bar/baz"))) class TestMatchNameComponent(unittest.TestCase):