Как отключить CherryPy без входящих подключений за указанное время? - PullRequest
0 голосов
/ 01 мая 2020

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

if timer >10 and connections == 0:
    close cherrypy (< I have a method for this already)

Я в основном манипулятор данных, поэтому не используется для веб-серверов. Поиск в Google показывает потерянные попадания при закрытии CherryPy, когда слишком много соединений, но не когда не было никаких соединений в течение указанного (короткого) времени. Я понимаю, что смысл веб-сервера обычно заключается в том, чтобы ждать в ожидании соединения, так что это может быть странным случаем. Все равно любая помощь приветствуется.

1 Ответ

2 голосов
/ 01 мая 2020

Интересный вариант использования, вы можете использовать инфраструктуру плагинов CherryPy, чтобы сделать что-то подобное, взгляните на реализацию этого плагина ActivityMonitor, он отключает сервер, если ничего не обрабатывает, и не видел ни одного запроса в указанном количество времени (в данном случае 10 секунд).

Возможно, вам придется настроить logi c на как , чтобы отключить его, или сделать что-нибудь еще в методе _verify.

Если вы хотите больше узнать об архитектуре публикации / подписки, взгляните на CherryPy Docs .

import time
import threading

import cherrypy
from cherrypy.process.plugins import Monitor


class ActivityMonitor(Monitor):

    def __init__(self, bus, wait_time, monitor_time=None):
        """
        bus: cherrypy.engine
        wait_time: Seconds since last request that we consider to be active.
        monitor_time: Seconds that we'll wait before verifying the activity.
                      If is not defined, wait half the `wait_time`.
        """
        if monitor_time is None:
            # if monitor time is not defined, then verify half
            # the wait time since the last request
            monitor_time  = wait_time / 2
        super().__init__(
            bus, self._verify, monitor_time, self.__class__.__name__
        )
        # use a lock to make sure the thread that triggers the before_request
        # and after_request does not collide with the monitor method (_verify)
        self._active_request_lock = threading.Lock()
        self._active_requests = 0
        self._wait_time = wait_time
        self._last_request_ts = time.time()

    def _verify(self):
        # verify that we don't have any active requests and
        # shutdown the server in case we haven't seen any activity
        # since self._last_request_ts + self._wait_time
        with self._active_request_lock:
            if (not self._active_requests and
                self._last_request_ts + self._wait_time < time.time()):
                self.bus.exit() # shutdown the engine

    def before_request(self):
        with self._active_request_lock:
            self._active_requests += 1

    def after_request(self):
        with self._active_request_lock:
            self._active_requests -= 1
        # update the last time a request was served
        self._last_request_ts = time.time()


class Root:

    @cherrypy.expose
    def index(self):
        return "Hello user: current time {:.0f}".format(time.time())


def main():
    # here is how to use the plugin:
    ActivityMonitor(cherrypy.engine, wait_time=10, monitor_time=5).subscribe()
    cherrypy.quickstart(Root())


if __name__ == '__main__':
    main()
...