Merge pull request #2206 from Suor/ssh-race

remote: fix race in and optimize SSHConnection.makedirs()
This commit is contained in:
Ruslan Kuprieiev
2019-06-28 14:09:04 +03:00
committed by GitHub
+13 -3
View File
@@ -1,6 +1,7 @@
import os
import posixpath
import logging
import errno
import stat
from contextlib import contextmanager
@@ -96,10 +97,13 @@ class SSHConnection:
def makedirs(self, path):
self._sftp_connect()
if self.isdir(path):
# Single stat call will say whether this is a dir, a file or a link
st_mode = self.st_mode(path)
if stat.S_ISDIR(st_mode):
return
if self.isfile(path) or self.islink(path):
if stat.S_ISREG(st_mode) or stat.S_ISLNK(st_mode):
raise DvcException(
"a file with the same name '{}' already exists".format(path)
)
@@ -110,7 +114,13 @@ class SSHConnection:
self.makedirs(head)
if tail:
self._sftp.mkdir(path)
try:
self._sftp.mkdir(path)
except IOError as e:
# Since paramiko errors are very vague we need to recheck
# whether it's because path already exists or something else
if e.errno == errno.EACCES or not self.exists(path):
raise
def walk(self, directory, topdown=True):
# NOTE: original os.walk() implementation [1] with default options was