Как запустить скрипт на минуту, остановить его выполнение, а затем запустить его снова? - PullRequest
0 голосов
/ 25 августа 2018

В настоящее время я работаю над сценарием, который должен быть запущен в течение определенного периода времени (скажем, минуты), а затем должен остановить его выполнение примерно на 5 секунд, а затем снова начать выполнение (этот цикл продолжаетсяповторяя), в обязательном порядке.Скрипт находится в Python 3.x и работает в среде Ubuntu.Таким образом, создание Service / Daemon того же самого также будет работать (хотя выполнение сценария должно быть остановлено на несколько секунд).

В основном используется модуль Scapy для прослушивания пакетов во время захвата Live и затем некоторого анализана этих захваченных пакетах, прежде чем вставлять данные в базу данных.Когда я останавливаю выполнение скрипта нажатием Ctrl+C, он останавливается, а затем вставляет данные в БД, а не параллельно.Хотя было бы лучше, если бы этот процесс выполнялся параллельно и сценарий никогда не прекращал выполняться, но до тех пор мне нужен обходной путь для этого.

Мой подход:

import scapy

def main():
    capture = LiveCapture(interface = "<some interface>", filter="<some filter>")
    count = 0
    for pkt in capture:
        #DO SOMETHING

        insert_in_DB()   #--------This happens only when I stop the execution.
        if count == 100:
            count = 0
            #back to main()

Итак, вы получили общее представление о том, что пытается делать мой код, верно?Но я хочу, чтобы это происходило через каждую 1 минуту, когда после выполнения в течение 1 минуты выполнение кода останавливается, чтобы данные могли быть введены в БД, а затем возобновлены через 5 или менее секунд.

Спасибо взаранее:)

1 Ответ

0 голосов
/ 25 августа 2018

Вы должны использовать MySQLdb для использования MySQL в Python и Twisted adbapi для выполнения асинхронных подключений.

MySQLdb:

sudo apt-get install python-dev
sudo apt-get install libmysqlclient-dev
pip3 install mysql-python

Витые адбапи:

pip3 install twisted

Spider.py

def parse(self, response):
    yield {
        'item_id' : ...
        'item_name': ...
        ...
    }

Добавьте MySQLStorePipeline к pipelines.py и объявите его в settings.py:

pipelines.py

from twisted.enterprise import adbapi       #pip3 install twisted
from scrapy import log
from scrapy.conf import settings
import MySQLdb.cursors

class MySQLStorePipeline(object):
    #A pipeline to store the item in a MySQL database.
    #This implementation uses Twisted's asynchronous database API.


    def __init__(self):
        dbargs = settings.get('DB_CONN')
        self.dbpool = adbapi.ConnectionPool(
            "MySQLdb",
            cursorclass=MySQLdb.cursors.DictCursor,
            **dbargs
        )

    def process_item(self, item, spider):
        # run db query in thread pool
        query = self.dbpool.runInteraction(self._conditional_insert, item)
        query.addErrback(self.handle_error)
        return item

    def _conditional_insert(self, tx, item):
        # create record if doesn't exist. 
        # all this block run on it's own thread
        item_id = item['item_id']
        db_table = 'your_table_name'

        try:
            tx.execute("SELECT 1 FROM " + db_table + " WHERE item_id = %s", (item_id, ))
        except:
            print("## Query Failed:" + str(tx._last_executed))

        result = tx.fetchone()

        if result:
            log.msg("Item already stored in db: %s" % item, level=log.DEBUG)
        else:
            try:
                tx.execute(\
                    "INSERT INTO " + db_table + " (item_id, item_name) "
                    "values (%s, %s)",
                    (item_id, item['item_name'])
                )
                log.msg("Item stored in db: %s" % item, level=log.DEBUG)
            except:
                print("## Query Failed:" + str(tx._last_executed))

    def handle_error(self, e):
        log.err(e)

Settings.py

ITEM_PIPELINES = {
    'your_project.pipelines.your_projectPipeline': 300,
    'your_project.pipelines.MySQLStorePipeline': 600,
} #note: https://stackoverflow.com/questions/37442907/scrapy-attributeerror-list-object-has-no-attribute-iteritems

DB_CONN = {    
    'db': 'your_db',
    'user': 'your_username',
    'passwd': 'your_password',
    'host': 'your_host',
    'charset': 'utf8',
    'use_unicode': True,
} 

примечания :

Замените все свои _ ***** вашими учетными данными SQL.

В приведенном выше коде предполагается, что ваш SQLТаблица имеет только 2 столбца: 'item_id', 'item_name', конечно, вы можете изменить его в запросе INSERT INTO.

Если у вас возникли проблемы, оставьте комментарий.

...