Python serial read fails for long period - python

I am using an accelerometer sensor in Node MCU to get 300 samples per second and store it for a week. My code below fails after some minutes.
import serial
ser = serial.Serial("COM5", 115200)
ser.flushInput()
i = 0
while True:
try:
i += 1
print (i)
ser_bytes = ser.readline()
print(ser_bytes)
except:
print("Keyboard Interrupt")
break
It failed after 4129 lines. I've attached the output

Related

Python Serial: having trouble reading the port

I'm attempting to read the values of some GPIO. Here's the code:
import serial
import codecs
import time
ser = serial.Serial(port = 'COM4', baudrate = 9600, \
parity = serial.PARITY_NONE, \
stopbits = serial.STOPBITS_ONE, \
bytesize = serial.EIGHTBITS, \
timeout = 0, \
)
print('connected to: ',ser.name)
ser.close()
def SSend(input):
ser.write(codecs.decode(input, "hex_codec")) #send as ASCII
print('sent: ', input)
def ReadIO():
#open the port
try:
ser.open()
except:
print('error opening serial port')
exit()
#flush the buffers
ser.flushInput()
ser.flushOutput()
#write data to read from GPIO
#causes SC18IM to return a byte containing each of the 8 I/O values
SSend(b'4950')
time.sleep(0.1) #allow time for the data to be received
#read the data
serialData = False
serialData = ser.readline()
ser.close()
return serialData
while 1:
print(ReadIO())
time.sleep(0.5)
This prints the following:
sent:
b'4950'
b''
(I am expecting back either 0x00 or 0x20 instead of an empty byte)
I know my hardware is good as is what I'm sending because it get back what I expect when using Realterm and have successful write commands in my script elsewhere.
I had some luck using this
#read the data
serialData = False
for c in ser.readline():
print('in loop')
print(c)
serialData = c
ser.close()
However, I don't really understand why it worked and it only appears to work intermittently.
Thanks for reading.
readline() assumes that there is some end-of-line symbol, like \n or \r. You should read data byte-wise:
serialData = ''
while ser.inWaiting() > 0:
c=ser.read(1)
# or c=ser.read(1).decode('latin1')
serialData += c

Python Serial stops reading

I'm working on a project with a coin acceptor and a raspberry. I have the following code to test the output from the coin acceptor:
import serial
from time import sleep
ser = serial.Serial('/dev/ttyUSB0', 4800, 8, 'N', 1, timeout=None)
while True:
line = ser.read(ser.inWaiting())
if len(line) > 0:
print ord(line)
ser.close()
everything works fine and i get output from the acceptor every time i drop a coin. But after a while it stops reading. In windows with a serial port monitor it works and I get output every time.
Thanks!
now i have modified the code, but there is the same behaviour as at the beginning. After a certain time it stops reading:
import serial
from time import sleep
ser = serial.Serial('/dev/ttyUSB0', 4800, bytesize=8, parity=serial.PARITY_EVEN, stopbits=1, timeout=0, rtscts=1)
sleep(3)
print("ready ..")
print(ser.isOpen())
while True:
line = ser.read()
if len(line) > 0:
print ser.isOpen()
print line
print ser.isOpen()
ser.close()
the output from ser.isOpen is always TRUE

How to Make Python-Twitter Work With Arduino

I'm trying to get my Arduino to ring a bell every time the #annoyingbellbot receives the #ringit message. I adapted a lot of this code this instructable but I changed some of it to work with the bell. By the way, I took the twitter API info out so I don't think that is the problem and assume all the spacing is correct. So my problem is that when I tweet at the #annoyingbellbot, nothing happens. It just stays in the loop forever. Any help would be greatly appreciated. Thanks!
##Import Libraries
import twitter
import serial
import time
##authenticate yourself with twitter
api = twitter.Api(consumer_key='', consumer_secret='', access_token_key='', access_token_secret='')
##set to your serial port
#ser = serial.Serial(port='COM3')
ser = serial.Serial()
ser.baudrate = 9600
ser.port = 3
## check serial port
def checkokay():
ser.flushInput()
time.sleep(3)
line=ser.readline()
time.sleep(3)
if line == ' ':
line=ser.readline()
print 'here'
## Welcome message
print 'Welcome To Bell Bot!'
def driptwit():
status = []
x = 0
drip = []
status = api.GetUserTimeline('annoyingbellbot') ##grab latest statuses
checkIt = [s.text for s in status] ##put status in an array
if len(status) != 0:
drip = checkIt[0].split() ##split first tweet into words
## check for match and write to serial if match
if drip[0] == '#ringit':
print 'Tweet Recieved, Ringing Bell'
ser.write('1')
else:
ser.write('0')
print 'Awaiting Tweet'
print "Loop"
while 1:
driptwit() ## call driptwit function
time.sleep(15) ## sleep for 15 seconds to avoid rate limiting

PySerial: how to understand that the timeout occured while reading from serial port?

I'm using PySerial to read from serial port like in the code below.
CheckReadUntil() read output of the command that I send to serial port until the sequence of symbols readUntil are in the serial output.
...
self.ser = serial.Serial(comDev, 115200, timeout=10)
...
#Function that continue to read from Serial port until 'readUntil'
#sequence of symbols appears
def CheckReadUntil(self, readUntil):
outputCharacters = []
while 1:
ch = self.ser.read()
outputCharacters += ch
if outputCharacters[-len(readUntil):]==readUntil:
break
outputLines = ''.join(outputCharacters)
return outputLines
However, if there is no sequence readUntil (for any reason), I'm just stuck in the function CheckReadUntil() forever. The setting timeout=10 sets up timeout so I'm stuck in a loop that iterates every 10 seconds and does nothing, just waiting.
How it is possible to understand that there was a timeout event so I may exit the infinite loop? Output length may be different.
UPDATE (previous answer was not correct, this is the working code from #konstantin):
...
self.ser = serial.Serial(comDev, 115200, timeout=10)
...
#Function that continue to read from Serial port until 'readUntil'
#sequence of symbols appears
def CheckReadUntil(self, readUntil):
outputCharacters = []
while 1:
ch = self.ser.read()
if len(ch) == 0:
break
outputCharacters += ch
if outputCharacters[-len(readUntil):]==readUntil:
break
outputLines = ''.join(outputCharacters)
return outputLines

How to read a string of integers received on python from serial arduino

I'm sending a list of values (e.g. 80,539,345,677) from Arduino to a Python app running on my RPi. I have not been successful in extracting the values and assigning them to respective variables or objects in the app.
Here's my code:
def read_values():
#if DEBUG:
print "reading arduino data"
ser = serial.Serial('/dev/ttyUSB0', 9600)
print "receiving arduino data"
ser_line = ser.readline()
print ser_line
ser.close()
ser_list = [int(x) for x in ser_line.split(',')]
ambientLight = ser_list[1]
print ambientLight
return ambientLight
What I'm getting from Python is:
reading arduino data
receiving arduino data
80,477,82,2
Traceback (most recent call last):
File "serialXivelyTest4c.py", line 77, in <module>
run()
File "serialXivelyTest4c.py", line 63, in run
ambientLight = read_values()
File "serialXivelyTest4c.py", line 27, in read_values
ser_list = [int(x) for x in ser_line.split(',')]
ValueError: invalid literal for int() with base 10: '8254\r80'
You can see that I'm getting values, but that they're being truncated. Can anyone please tell me where I'm going wrong here. Thanks so much.
I've never used an Arduino but here's how I read from serial with a different board. I used serial.
import streamUtils as su # see below
ser = su.connectPort("/dev/tty.SLAB_USBtoUART") # make sure you have the right port name
data = ""
while True:
try:
data = data + ser.read(1) # read one, blocking
time.sleep(1) # give it time to put more in waiting
n = ser.inWaiting() # look if there is more
if n:
data = data + ser.read(n) # get as much as possible
# I needed to save the data until I had complete
# output.
if data:
# make sure you have the whole line and format
else:
break
except serial.SerialException:
sys.stderr.write("Waiting for %s to be available" % (ser.name))
sys.exit(1)
sys.stderr.write("Closing port\n")
ser.close()
Here's the streamUtils.connectPort():
import serial
def connectPort(portname):
# connect to serial port
ser = serial.Serial()
ser.port = portname
ser.baudrate = 9600
ser.parity = serial.PARITY_NONE
ser.stopbits = serial.STOPBITS_ONE
ser.bytesize = serial.EIGHTBITS
ser.timeout = 15 # need some value for timeout so the read will end
try:
ser.open()
except serial.SerialException:
sys.stderr.write("Could not open serial port %s\n" % (ser.name))
sys.exit(1)
return (ser)

Categories

Resources