I am using 2 raspberry pi and each of them has a camera connected.
I am trying to run, from the first pi, a script to get the video feed of the second one.
And for that, I would need the value my function returns through ssh.
With a simple example :
slaveScript.py
def run():
return "hello there"
if __name__ == '__main__':
run()
masterScript.py
import pexpect
try:
# ssh connection
child = pexpect.spawn('ssh -X pi@pislave.local')
child.expect('pi@pislave.local's password:', timeout=10)
child.sendline('pi')
child.expect('$')
# run script
child.sendline('python3 slaveScript.py run')
cap = child.read() # error here
print(cap)
except pexpect.ExceptionPexpect as e:
print(str(e))
I would like, for this example to get “hello there”. How can I get it? Is there a pexpect method I can use?
In context with the cameras :
SlaveScript.py
import cv2
def run():
return cv2.VideoCapture(0)
if __name__ == '__main__':
run()
MasterScript.py
import pexpect
import cv2
try:
# ssh connection
child = pexpect.spawn('ssh -X pi@pislave.local')
child.expect('pi@pislave.local's password:', timeout=10)
child.sendline('pi')
child.expect('$')
# run script to read and show the video feed
while True:
child.sendline('python3 SlaveScript.py')
cap = child.read()
ret, frame = cap.read()
cv2.imshow('slaveCam', frame)
except pexpect.ExceptionPexpect as e:
print(str(e))
I know that it works if I put the lines from while True
to cv2.imshow
in the slave script. I have a window opening and a video feed of around 1 image every 3 seconds (I don’t care about performance).
However, the video feed will have to be implemented inside a kivy GUI, so I need to get the frame
in my master script so that I can put it in a texture in kivy.
Is there any way to do it?
Advertisement
Answer
I think you are on the wrong track with pexpect
. You should be using password-less login by copying your public RSA key to the slave device – then you can get rid of all the awkwardness of pexpect
.
Also, I would consider using Redis. It is very fast, and lightweight and it serves integers, strings, lists, sets, hashes from memory (RAM) across a network.
Simply stuff the frames of video in Redis on the slave, either as JPEGs, or PNGs or Numpy arrays and call it latestFrame
. That looks like:
redis.set('latestFrame', frame)
On the other machine, just grab latestFrame
from Redis and display it. That looks like:
frame = redis.get('latestFrame')
Example here.