Adam
Adam

Reputation: 4227

Reading json object from serial port

I want to use ijson to read an object from a serial port. I can read from the port fine, and I can use ijson to deserialize an object from a stream, but using ijson from a serial port just isn't enumerating anything.

This is an example of my code:

    self.serial_port = serial.Serial(
        port=self.port_name, \
        baudrate=115200, \
        parity=serial.PARITY_NONE, \
        stopbits=serial.STOPBITS_ONE, \
        bytesize=serial.EIGHTBITS, \
        timeout=None)
    print 'start reading'
    parser = ijson.parse(self.serial_port)

    for prefix, event, value in parser:
        print `value`
    print 'stop reading'

and my output is just

    start reading

Upvotes: 0

Views: 1183

Answers (2)

Adam
Adam

Reputation: 4227

Ok, I figured it out. You have to set the buffer size to 1. So, this works...

objects = ijson.common.items(ijson.parse(self.serial_port, buf_size=1), 'item')
    for o in objects:
        print `o`

My goal was to be able to receive an endless stream of objects. I signal the start of the stream with "[", then send a comma separated list of json objects, and terminate the list with "]". Every time an object is completed within the array, the iterator loops.

Works perfectly.

Test by sending it this (intentional newline in the middle of the object):

[{"foo": "bar"}, {"bar":
"foo"}]

Upvotes: 0

Dennis Shtatnov
Dennis Shtatnov

Reputation: 1363

Try doing:

import ijson
import sys
for x in ijson.parse(sys.stdin):
    print(x)

You can type in json but nothing will print out until you press Ctrl-D twice to signal the end of stdin.

I haven't tested it, but I suspect that something similar is happening with your serial port: because your serial port never closes, ijson doesn't know when to start parsing. Depending on your serial libraries, I would try to send an EOF or EOT character to python or separately find a way to make it trigger the end of the stream.

Some options I can think off:

  • Read a single line separately from ijson and then parse it
  • Set a timeout or a inter_byte_timeout to only read the first segment of json from the stream

Upvotes: 1

Related Questions