Python Asyncio How to itertools.cycle с более чем 1 запросом одновременно
Я использую Sanic, мы используем прокси-сервер для создания внешних подключений для удаления из Интернета.
Я хочу создать python dict и поместить список прокси внутри python dict. В рамках этого условия мы будем хранить такие значения, как 0
, 1
, 1
= прокси не удалось подключиться.
Я рассчитываю на равномерный доступ к списку, поэтому наши прокси имеют некоторую предсказуемую схему их использования с течением времени. Вместо случайного выбора их, что может привести к интенсивному использованию одного прокси над другими.
Тем не менее, так как Sanic имеет ряд рабочих. Я пытаюсь понять, как справиться с этим.
Визуально мои мысли таковы, что это будет похоже на линию прокси-серверов, каждый раз, когда его просят, прокси-сервер сверху делает следующий шаг, и как только его вызывают, он снова переходит в конец строки.
Что-то вроде https://docs.python.org/2/library/itertools.html кажется отличным вариантом.
Тем не менее, мой вопрос... Как это может произойти асинхронно и без блокировки. Как рабочий или запрос может произойти одновременно. Как это решить, если запрос 2-50 происходит одновременно.
1 ответ
Ваш лучший выбор может быть, чтобы посмотреть на что-то вроде Aredis. Рабочие по сути являются подпроцессами, поэтому общий диктат не будет работать.
Если вы посмотрите в исходном коде, где используются рабочие параметры, то ниже в методе serve_multiple.
def serve_multiple(server_settings, workers):
"""Start multiple server processes simultaneously. Stop on interrupt
and terminate signals, and drain connections when complete.
:param server_settings: kw arguments to be passed to the serve function
:param workers: number of workers to launch
:param stop_event: if provided, is used as a stop signal
:return:
"""
server_settings['reuse_port'] = True
# Handling when custom socket is not provided.
if server_settings.get('sock') is None:
sock = socket()
sock.setsockopt(SOL_SOCKET, SO_REUSEADDR, 1)
sock.bind((server_settings['host'], server_settings['port']))
sock.set_inheritable(True)
server_settings['sock'] = sock
server_settings['host'] = None
server_settings['port'] = None
def sig_handler(signal, frame):
logger.info("Received signal %s. Shutting down.", Signals(signal).name)
for process in processes:
os.kill(process.pid, SIGINT)
signal_func(SIGINT, lambda s, f: sig_handler(s, f))
signal_func(SIGTERM, lambda s, f: sig_handler(s, f))
processes = []
for _ in range(workers):
process = Process(target=serve, kwargs=server_settings)
process.daemon = True
process.start()
processes.append(process)
for process in processes:
process.join()
# the above processes will block this until they're stopped
for process in processes:
process.terminate()
server_settings.get('sock').close()
Redis имеет очередь, так что вы можете удалить что-то из очереди, а затем заменить ее, если это необходимо.
Я представляю себе прокси, которого вы могли бы достичь с помощью nginx?