从sys.stdin读取,没有换行符或EOF

问题描述 投票:4回答:3

我想从我的gps跟踪器中接收数据。它通过tcp发送数据,因此我使用xinetd侦听一些tcp端口和python脚本来处理数据。这是xinetd配置:

service gps-gprs
{
    disable     = no
    flags       = REUSE
    socket_type = stream
    protocol    = tcp
    port    = 57003
    user        = root
    wait        = no
    server      = /path/to/gps.py
    server_args     = 3
} 

在/ etc / services中配置

gps-gprs        57003/tcp           # Tracking system

和Python脚本gps.py

#!/usr/bin/python
import sys

def main():
    data = sys.stdin.readline().strip() 
    #do something with data
    print 'ok'

if __name__ =='__main__':
    main()

跟踪器以原始文本形式发送数据字符串,例如

$GPRMC,132017.000,A,8251.5039,N,01040.0065,E,0.00,,010111,0,,A*75+79161234567#

问题是python脚本中的sys.stdin无法接收行尾或文件字符结尾,并且sys.stdin.readline()永远消失了。我试图用python脚本从另一台PC发送数据

import socket
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(('', 57003))
s.sendall( u'hello'  )
data = s.recv(4024)
s.close()
print 'Received', data

并且如果消息为'hello',则失败,但是如果消息为'hello \ n',则表示一切正常。但是我不知道ho告诉tracker或xinetd在消息末尾添加此“ \ n”。如何在没有EOF或EOL的情况下从sys.stdin中读取数据?

python tcp tcplistener xinetd
3个回答
6
投票

sys.stdin.readline()永远等待直到收到换行符。然后,它认为当前行已完成并完整返回。如果您想读取不包含换行符的数据,或者不想等到收到换行符后再处理(某些)数据,那么您将不得不使用readline以外的其他内容。您很可能应该调用read,它可以读取任意大小的给定数据。

但是,您的GPS似乎正在以众所周知的NEMA格式发送数据,并且该格式肯定以换行符结束了每一行。实际上,它可能以CRLF(\r\n)终止每行,但是\r可能在进入TCP套接字之前被割断了。无论哪种方式,每行的结尾处都有一个'\ n`。

如果您的readline呼叫挂起而没有返回任何行,则很可能是因为发送方正在缓冲行,直到它具有完整的缓冲区为止。如果您等待了足够长的时间以使发送者的缓冲区填满,那么您将一次获得一整行。如果发生了这种情况,则必须将发送方更改为在每个NEMA语句之后刷新发送缓冲区。


8
投票

简单:

data=sys.stdin.read().splitlines()

for i in data:
        print i

无换行符


2
投票

似乎您正在接收#而不是<CR><LF>,只需阅读直到#符号。

data = ""
while len(data) == 0 or data[-1] <> '#':
    data += sys.stdin.read(1)

#do something with data
print 'ok'
© www.soinside.com 2019 - 2024. All rights reserved.