Reputation: 6215
I am hoping this is a simple stupid noob mistake that can be fixed with the addition of a single line of code somewhere.
I'm using pySerial to read in serial data from a USB port and print it out to standard output. I'm running Mac OSX 10.6. I open terminal and type "python", then the following:
>>> import serial;
>>> ser = serial.Serial('/dev/tty.usbserial-XXX', 9600, timeout=1);
>>> while True:
>>> if ser.inWaiting() > 0:
>>> ser.readline();
>>> [done, I hit enter...]
This works beautifully. It starts outputting my serial data nicely, exactly as I'd expect it to. Great, I think, let me put this into its own script with command line arguments and then I can call it any time I want to:
import sys;
import serial;
serialPort = sys.argv[1]
baudRate = sys.argv[2]
ser = serial.Serial(serialPort, baudRate, timeout=1)
while True:
if ser.inWaiting() > 0:
ser.readline()
On the command line, I type "python myScript.py [my serial port] 9600" and sit back and wait for a beautiful flow of serial data - but nothing comes out. It just kinda hangs until I kill the process.
I thought, well maybe for some reason it's not working - so I put some debugging prints into the code. I update my while loop to look like this:
while True:
print("looping...")
print(ser.inWaiting());
if ser.inWaiting() > 0:
ser.readline()
I run it again, and I get a repeating output stream of "Looping..." and "0". I think, well maybe there's something wrong with my command line arguments - so I hard-coded the port and the baud rate into the script, same thing.
So, why would this be the case? Is my use of while True: somehow blocking the script from accepting serial data? Is there a better way to do this?
I'm a complete Python noob. I am writing this script in order to create a faster way to communicate between Adobe AIR and an Arduino board. I'm hoping there's a magic bullet I can drop in here to make it work - is there?
Upvotes: 3
Views: 1146
Reputation: 38462
Is my use of while True: somehow blocking the script from accepting serial data?
Nope. This is very standard practice and doesn't affect I/O in any way. while True
is very much equivalent to while 1
in C.
Is there a better way to do this?
I'm concerned about your arguments, like others. This should be more reliable overall:
from sys import argv
from serial import Serial
try:
baudRate = int(argv[-1])
serialPort = argv[1:-1]
except ValueError:
#some nice default
baudRate = 9600
serialPort = argv[1:]
#support paths with spaces. Windows maybe?
serialPort = ' '.join(serialPort)
if not serialPort:
exit("Please specify a serial port")
print( "reading from %r@%i ..." % (serialPort, baudRate) )
ser = Serial(serialPort, baudRate, timeout=1)
while True:
if ser.inWaiting() > 0:
print( ser.readline() )
If that doesn't help you, please check that you are using the same interpreter by running these lines in a script and in the CLI.
import sys
print("Executable: " + sys.executable)
print("Version: " + sys.version)
Upvotes: 0
Reputation: 1420
Is it printing anything? I'd assume it would print:
looping...
<ser.inWaiting() val>
And then nothing. Add a print statement so it looks like
print ser.readline()
and see if that works. I'm guessing that the interpreter is printing the returned strings when you do it as a command, but in a script the returned strings from readline() are getting discarded.
Upvotes: 1
Reputation: 15198
In your 1st example, baud rate is an integer but in the 2nd, you don't not convert sys.argv[2]
from a string. Try this ser = serial.Serial(serialPort, int(baudRate), timeout=1)
.
Upvotes: 1