#python #multithreading #fabric #put #mkstemp
#python #многопоточность #fabric #поместите #mkstemp
Вопрос:
Версия Python: 2.6.4
Версия Fabric: 1.9.0
У меня есть платформа тестирования автоматизации для параллельного выполнения обращений с использованием многопоточности.Поток (3 потока в моем случае).
Каждый рабочий поток использует fabric put (хотя мы делаем некоторую оболочку для этой функции), чтобы скопировать временный файл, созданный tempfile.mkstemp, в удаленный файл.
Вопрос в том, что он всегда выдает мне сообщение об ошибке, что файл не может быть найден, ошибка возникает во время «ввода» из подсказок об исключениях.
вот код при выполнении ‘put’:
MyShell.py (Родительский класс MyFabShell)
def putFileContents(self, file, contents):
fd, tmpFile= tempfile.mkstemp()
os.system('chmod 777 %s' % tmpFile)
contentsFile = open(tmpFile, 'w')
contentsFile.write(contents)
contentsFile.close()
dstTmpFile = self.genTempFile()
localshell = getLocalShell()
self.get(localshell, tmpFile, dstTmpFile) # use local shell to put tmpFile to dstTmpFile
os.close(fd)
os.remove(tmpFile)
#os.remove(tmpFile)
MyFabShell.py:
def get( self, srcShell, srcPath, dstPath ):
srcShell.put( self, srcPath, dstPath )
def put(self, dstShell, srcpath, dstpath):
if not self.pathExists( srcPath ): # line 158
raise Exception( "Cannot put <%s>, does not exist." % srcPath )
# do fabric get/put in the following
# ...
Вызов put приводит к ошибке:
...
self.shell.putFileContents(configFile, contents)
File "/path/to/MyShell.py", line 401, in putFileContents
self.get(localShell, tmpFile, dstTmpFile)
File "/path/to/MyFabShell.py", line 134, in get
srcShell.put( self, srcPath, dstPath )
File "/path/to/myFabShell.py", line 158, in put
raise Exception( "Cannot put <%s>, does not exist." % srcPath )
Exception: Cannot put </tmp/tmpwt3hoO>, does not exist.
Изначально я сомневаюсь, что файл может быть удален во put
время, поэтому я прокомментировал os.remove
. Однако я снова получил ту же ошибку.
Из журнала исключений это не должно быть проблемой «fabric put», поскольку исключение возникает перед выполнением fabric get / put
mkstemp
Небезопасно ли использовать многопоточность? но в документе говорится, что «При создании файла нет условий гонки» или мой случай терпит неудачу из-за GIL? Я подозреваю, что это связано с тем, что, когда я использую только 1 поток, все будет хорошо.
Кто-нибудь может дать мне подсказку о моей ошибке? Некоторое время я боролся с проблемой: (
Комментарии:
1. Когда происходит обработка потоков? Этот код уже находится в потоке, или это происходит в myput ? Также не могли бы вы указать трассировку стека? И / или общее представление о том, что происходит в вашей оболочке?
2. Спасибо @Morgan, я уточнил свои вопросы с помощью кода режима, а также журналов.
3. Моя проблема решается, когда я явно «присоединяюсь» к потоку. все мои потоки не являются потоками демонов, и каждый из потоков выполняет большую часть операций ввода-вывода (например, запись / чтение файла). ‘join’ явно гарантирует, что задание каждого потока завершено. Я все еще не уверен в основной причине моей проблемы … временный файл на самом деле существует, но поток жалуется «не удается найти», единственное предположение, которое я могу дать, это то, что мы всегда должны явно присоединяться, особенно когда ваше задание потока связано с операцией ввода-вывода?
Ответ №1:
Моя проблема решается, когда я явно «присоединяюсь» к потоку. все мои потоки не являются потоками демонов, и каждый из потоков выполняет большую часть операций ввода-вывода (например, запись / чтение файла). ‘join’ явно гарантирует, что задание каждого потока завершено. Я все еще не уверен в основной причине моей проблемы … временный файл на самом деле существует, но поток жалуется на «не удается найти», когда несколько потоков работают вместе, единственное предположение, которое я могу дать: когда поток A выполняет операцию ввода-вывода, поток A освобождает GIL, чтобы потокB (или C, D …) может получить GIL во время операции ввода-вывода. проблема может возникнуть во время ввода-вывода, потому что поток A больше не находится в интерпретаторе Python … вот почему «файл не может быть найден» с помощью A, однако, когда мы явно присоединяемся к A, A всегда обязательно завершает свою работу, повторно вводя GI (глобальный интерпретатор).