Как заблокировать выполнение двух экземпляров той же программы?

Было бы более надежно использовать ожидаемое условие

pages = WebDriverWait(driver,5).until(EC.presence_of_all_elements_located((By.CSS_SELECTOR, '.artdeco-pagination__indicator')))

Дополнительный импорт

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
22
задан Tomas Sedovic 5 October 2008 в 00:05
поделиться

8 ответов

Существует несколько методов, которые можно использовать для выполнения только разрешения одного экземпляра приложения:

Метод 1: Глобальный объект синхронизации или память

Это обычно делается путем создания именованного глобального взаимного исключения или события. Если это уже создается, то Вы знаете, что программа уже работает.

, Например, в окнах Вы могли сделать:

    #define APPLICATION_INSTANCE_MUTEX_NAME "{BA49C45E-B29A-4359-A07C-51B65B5571AD}"

    //Make sure at most one instance of the tool is running
    HANDLE hMutexOneInstance(::CreateMutex( NULL, TRUE, APPLICATION_INSTANCE_MUTEX_NAME));
    bool bAlreadyRunning((::GetLastError() == ERROR_ALREADY_EXISTS));
    if (hMutexOneInstance == NULL || bAlreadyRunning)
    {
        if(hMutexOneInstance)
        {
            ::ReleaseMutex(hMutexOneInstance);
            ::CloseHandle(hMutexOneInstance);
        }
        throw std::exception("The application is already running");
    }

Метод 2: Блокировка файла, вторая программа не может открыть файл, таким образом, это, открывают

You мог также исключительно открытый файл путем блокировки его на открытом приложении. Если файл уже исключительно открыт, и Ваше приложение не может получить дескриптор файла, то это означает, что программа уже работает. На окнах Вы просто не определили бы совместное использование флагов FILE_SHARE_WRITE на файле, который Вы открываете с CreateFile API. На Linux Вы использовали бы flock.

Метод 3: Поиск имени процесса:

Вы могли перечислить активные процессы и искать один с Вашим именем процесса.

33
ответ дан 29 November 2019 в 04:27
поделиться

Будьте осторожны, , программа единственного экземпляра является своим собственным отказом в обслуживании .

ссылка описывает проблему безопасности единственного обнаружения экземпляра и предлагает использовать securable метод так, по крайней мере, процессы более низких прав не могут использовать проблему.

5
ответ дан 21 July 2019 в 15:25
поделиться

Ваш метод записи процесса, изодромного с предварением в файл, является общим, который используется во многих различных установленных приложениях. На самом деле, если Вы смотрите в Вашем /var/run каталог прямо сейчас, я держал пари, что Вы уже найдете несколько *.pid файлы.

, Как Вы говорите, это не на 100% устойчиво, потому что существует шанс pids, запутывающегося. Я услышал о программах с помощью flock() для блокировки специализированного файла, который будет автоматически разблокирован ОС, когда процесс выйдет, но этот метод является более определенным для платформы и менее прозрачным.

5
ответ дан 29 November 2019 в 04:27
поделиться

Это - очень неUnix, чтобы запретить, что несколько экземпляров программы работают.

, Если программа является, скажем, сетевым демоном, она не должна активно запрещать несколько экземпляров - только первая инстанция добирается для слушания сокета, таким образом, последующие экземпляры разбомбили автоматически. Если это - скажем, RDBMS, это не должно активно запрещать несколько экземпляров - только первая инстанция добирается, чтобы открыть и заблокировать файлы. и т.д.

4
ответ дан 29 November 2019 в 04:27
поделиться

Я на самом деле использую точно процесс, который Вы описываете, и он хорошо работает за исключением пограничного случая, который происходит, когда Вы внезапно заканчиваетесь дисковое пространство и больше не можете создавать файлы.

"корректный" способ сделать это должно, вероятно, использовать общую память: http://www.cs.cf.ac.uk/Dave/C/node27.html

3
ответ дан 29 November 2019 в 04:27
поделиться

Если Вы хотите что-то, что это - стандарт трясины, то использование файла как 'блокировка' является в значительной степени способом пойти. Это действительно имеет недостаток, который Вы упомянули (если Ваше приложение не моется, перезапуск может быть проблемой).

Этот метод используется довольно многими приложениями, но единственным, который я могу вспомнить первое, что пришло на ум, является VMware. И да, существуют времена, когда необходимо войти и удалить '*.lck', когда вещи втиснуты.

Используя глобальное взаимное исключение или другой системный объект, как упомянуто Brian Bondy является лучшим способом пойти, но это конкретная платформа, (если Вы не пользуетесь некоторой другой библиотекой для абстракции специфических особенностей платформы далеко).

1
ответ дан 29 November 2019 в 04:27
поделиться

У меня нет хорошего решения, но двух мыслей:

  1. Вы могли добавить возможность ping запросить другой процесс и удостовериться, что это не несвязанный процесс. Firefox делает что-то подобное на Linux и не запускает новый экземпляр, когда каждый уже работает.

  2. при использовании обработчика сигналов можно удостовериться, что изодромный с предварением файл удален на всех кроме kill -9

0
ответ дан 29 November 2019 в 04:27
поделиться

Я сканирую список процессов, ища название моего исполняемого файла приложений с соответствием параметрам командной строки, тогда выходят, если существует соответствие.

Мое приложение может работать несколько раз, но я не хочу его выполняющий тот же файл конфигурации одновременно.

, Очевидно, это - конкретный Windows, но то же понятие довольно снисходительно относится, любой *ОТКЛОНЯЕТ систему даже без определенных библиотек просто путем открытия PS 'команды оболочки-ef' или изменения и поиска приложения.

   '*************************************************************************
   '     Sub: CheckForProcess()
   '  Author: Ron Savage
   '    Date: 10/31/2007
   '
   ' This routine checks for a running process of this app with the same
   ' command line parameters.
   '*************************************************************************
   Private Function CheckForProcess(ByVal processText As String) As Boolean
      Dim isRunning As Boolean = False
      Dim search As New ManagementObjectSearcher("SELECT * FROM Win32_process")
      Dim info As ManagementObject
      Dim procName As String = ""
      Dim procId As String = ""
      Dim procCommandLine As String = ""

      For Each info In search.Get()
         If (IsNothing(info.Properties("Name").Value)) Then procName = "NULL" Else procName = Split(info.Properties("Name").Value.ToString, ".")(0)
         If (IsNothing(info.Properties("ProcessId").Value)) Then procId = "NULL" Else procId = info.Properties("ProcessId").Value.ToString
         If (IsNothing(info.Properties("CommandLine").Value)) Then procCommandLine = "NULL" Else procCommandLine = info.Properties("CommandLine").Value.ToString

         If (Not procId.Equals(Me.processId) And procName.Equals(processName) And procCommandLine.Contains(processText)) Then
            isRunning = True
         End If
      Next

      Return (isRunning)
   End Function
0
ответ дан 29 November 2019 в 04:27
поделиться
Другие вопросы по тегам:

Похожие вопросы: