Я бы хотел запустить некоторых пауков с интервалом 30 минут. Мой код сейчас:
from threading import Timer
import subprocess
import os
import atexit
'''
Works but only in main thread. Kept for reference.
import scrapy
from scrapy.crawler import CrawlerProcess
from scrape_proxies.spiders.get_spys import Proxier
def run():
process = CrawlerProcess()
process.crawl(Proxier)
# process.crawl(MySpider2)
process.start() # the script will block here until all crawling jobs are finished
'''
def run():
def killChildren():
print("Killing children processes")
scraper1.kill()
# Spider 1
spider_name = 'get_spys'
scraper1 = subprocess.call(['scrapy', 'crawl', spider_name])
# Spider 2...
# Make sure subprocesses get killed when main process exits
atexit.register(killChildren)
class PerpetualTimer:
def __init__(self, t, hFunction):
self.t = t
self.hFunction = hFunction
self.thread = Timer(self.t, self.handle_function)
def handle_function(self):
self.hFunction()
self.thread = Timer(self.t, self.handle_function)
self.thread.start()
def start(self):
self.thread.start()
def cancel(self):
self.thread.cancel()
if __name__ == "__main__":
SCRAPER_TIMER = os.getenv('SCRAPER_TIMER', 1800)
print("Started runner.")
t = PerpetualTimer(SCRAPER_TIMER, run)
t.start()
Код работает, как и ожидалось, но я не могу понять, как убить подпроцесс на выходе основного потока / процесса. если я запускаю python runner.py и закрываю процесс, сканер все еще работает в фоновом режиме. Я хотел бы использовать прокомментированный код, но я продолжаю получать ValueError: сигнал работает только в основном потоке . Есть ли другой лучший способ запустить это?
Редактировать:
Решение, которое делает трюк, заключается в следующем, но использует time.sleep () , и это совсем не элегантно и Я хотел бы, чтобы программа запускалась с заданным интервалом с момента последнего запуска (если для запуска скребка требуется 5 минут, он должен запускаться через 25 минут, time.sleep запускается через 30 минут после завершения очистки).
import os
from scrapy.crawler import CrawlerProcess
import time
from scrape_proxies.spiders.get_spys import Proxier
def run():
process = CrawlerProcess()
process.crawl(Proxier)
# process.crawl(MySpider2)
process.start() # the script will block here until all crawling jobs are finished
if __name__ == "__main__":
SCRAPER_TIMER = os.getenv('SCRAPER_TIMER', 1800)
print("Started runner.")
while True:
run()
time.sleep(SCRAPER_TIMER)