Как прослушать HTTP-запросы и последовательный канал в одной и той же программе Python? - PullRequest
2 голосов
/ 24 марта 2012

У меня есть плата Arduino, подключенная к последовательному порту моего компьютера. Плата отправляет данные на ПК, но также может принимать заказы по тому же каналу. Однако между отправленными данными и заказами нет никакой связи или последовательности.

На ПК я создал демона, который прослушивает последовательный порт. И для отправки данных в Arduino я думал о создании сервера RPC XML внутри демона. Проблема в том, что я не знаю, как прослушивать последовательный порт и посещать XML-запрос RPC в той же программе.

Изначально у меня было что-то вроде этого:

while true
    if there is incoming data in the serial channel
       blah blah

    if there are HTTP requests
        start attending the XML RPC request

Серверы, на которые я смотрел (SimpleXMLRPCServer, web.py), постоянно прослушивают и обрабатывают запросы. Я хотел бы сказать своему серверу XML RPC: «подождите, если нет запросов, мы собираемся проверить последовательный канал».

Как мне достичь этого или чего-то подобного? Или я должен изменить свой дизайн? Если у меня есть сервер XML RPC в другом процессе, я думаю, что мне понадобится какое-то межпроцессное взаимодействие, именно поэтому я начал использовать XML RPC.

Ответы [ 2 ]

2 голосов
/ 24 марта 2012

Другой (и, вероятно, лучший) подход заключается в переносе приложения на асинхронный I / O . Например, вы можете использовать витую структуру (например, Twisted ) для одновременной асинхронной обработки HTTP и последовательного трафика в двух отдельных обработчиках протокола.

Примерно так:

from twisted.web import server, resource
from twisted.internet import protocol, reactor
from twisted.internet.serialport import SerialPort

class Echo(protocol.Protocol):
    def dataReceived(self, data):
        self.transport.write(data)

class HttpResource(resource.Resource):
    isLeaf = True

    def render_GET(self, request):
        request.setHeader("content-type", "text/plain")
        return "Hello there\n"

reactor.listenTCP(8080, server.Site(HttpResource()))
SerialPort(Echo(), <your serial port>, reactor, baudrate=9600)

reactor.run()
0 голосов
/ 24 марта 2012

Вы можете использовать то, что называется программой с потоками. Позволяет выполнять несколько действий параллельно.

Если вы используете Python, у вас есть больше информации здесь: http://docs.python.org/library/threading.html#thread-objects

Тем не менее, нити могут быть трудными для правильного использования. Существует несколько руководств по созданию потоков на Python, не стесняйтесь проверять их с помощью поисковой системы.

Большая идея сделать что-то подобное:

import threading

def processCommands():
    while True:
        #wait and process commands

def readSerial():
    while True:
        #read serial

serialThread = threading.Thread(target=readSerial)
commandThread = threading.Thread(target=processCommands)
serialThread.start()
commandThread.start()

#Wait for the command thread to exit,
#otherwise the programs would immediately exit
commandThread.join()
...