2019-03-06 02:01:17 +01:00
|
|
|
import os
|
|
|
|
import shutil
|
|
|
|
import tempfile
|
|
|
|
import time
|
|
|
|
|
2019-07-15 14:12:00 +02:00
|
|
|
from flask import Response, Blueprint, send_from_directory
|
2019-03-06 02:01:17 +01:00
|
|
|
|
|
|
|
from platypush.backend.http.app import template_folder
|
2019-07-15 14:12:00 +02:00
|
|
|
from platypush.backend.http.app.utils import authenticate, send_request
|
2019-03-06 02:01:17 +01:00
|
|
|
|
|
|
|
camera = Blueprint('camera', __name__, template_folder=template_folder)
|
|
|
|
|
|
|
|
# Declare routes list
|
|
|
|
__routes__ = [
|
|
|
|
camera,
|
|
|
|
]
|
|
|
|
|
2019-07-15 14:12:00 +02:00
|
|
|
|
2019-03-06 02:01:17 +01:00
|
|
|
def get_device_id(device_id=None):
|
|
|
|
if device_id is None:
|
|
|
|
device_id = str(send_request(action='camera.get_default_device_id').output)
|
|
|
|
return device_id
|
|
|
|
|
|
|
|
|
|
|
|
def get_frame_file(device_id=None):
|
|
|
|
device_id = get_device_id(device_id)
|
|
|
|
was_recording = True
|
|
|
|
frame_file = None
|
|
|
|
status = send_request(action='camera.status', device_id=device_id).output
|
|
|
|
|
|
|
|
if device_id not in status:
|
|
|
|
was_recording = False
|
2019-07-15 14:12:00 +02:00
|
|
|
send_request(action='camera.start_recording',
|
|
|
|
device_id=device_id)
|
2019-03-06 02:01:17 +01:00
|
|
|
|
|
|
|
while not frame_file:
|
|
|
|
frame_file = send_request(action='camera.status', device_id=device_id). \
|
|
|
|
output.get(device_id, {}).get('image_file')
|
|
|
|
|
|
|
|
if not frame_file:
|
|
|
|
time.sleep(0.1)
|
|
|
|
|
|
|
|
if not was_recording:
|
|
|
|
with tempfile.NamedTemporaryFile(prefix='camera_capture_', suffix='.jpg',
|
|
|
|
delete=False) as f:
|
2019-07-15 14:12:00 +02:00
|
|
|
# stop_recording will delete the temporary frames. Copy the image file
|
|
|
|
# to a temporary file before stopping recording
|
2019-03-06 02:01:17 +01:00
|
|
|
tmp_file = f.name
|
|
|
|
|
|
|
|
shutil.copyfile(frame_file, tmp_file)
|
|
|
|
frame_file = tmp_file
|
|
|
|
send_request(action='camera.stop_recording', device_id=device_id)
|
|
|
|
|
|
|
|
return frame_file
|
|
|
|
|
|
|
|
|
|
|
|
def video_feed(device_id=None):
|
|
|
|
device_id = get_device_id(device_id)
|
|
|
|
send_request(action='camera.start_recording', device_id=device_id)
|
|
|
|
last_frame_file = None
|
|
|
|
|
|
|
|
try:
|
|
|
|
while True:
|
|
|
|
frame_file = get_frame_file(device_id)
|
|
|
|
if frame_file == last_frame_file:
|
|
|
|
continue
|
|
|
|
|
|
|
|
with open(frame_file, 'rb') as f:
|
|
|
|
frame = f.read()
|
|
|
|
|
|
|
|
yield (b'--frame\r\n'
|
|
|
|
b'Content-Type: image/jpeg\r\n\r\n' + frame + b'\r\n')
|
|
|
|
|
|
|
|
last_frame_file = frame_file
|
|
|
|
finally:
|
|
|
|
send_request(action='camera.stop_recording', device_id=device_id)
|
|
|
|
|
|
|
|
|
|
|
|
@camera.route('/camera/<device_id>/frame', methods=['GET'])
|
2019-07-15 14:12:00 +02:00
|
|
|
@authenticate()
|
2019-03-06 02:01:17 +01:00
|
|
|
def get_camera_frame(device_id):
|
|
|
|
frame_file = get_frame_file(device_id)
|
|
|
|
return send_from_directory(os.path.dirname(frame_file),
|
|
|
|
os.path.basename(frame_file))
|
|
|
|
|
2019-07-15 14:12:00 +02:00
|
|
|
|
2019-03-06 02:01:17 +01:00
|
|
|
@camera.route('/camera/frame', methods=['GET'])
|
2019-07-15 14:12:00 +02:00
|
|
|
@authenticate()
|
2019-03-06 02:01:17 +01:00
|
|
|
def get_default_camera_frame():
|
|
|
|
frame_file = get_frame_file()
|
|
|
|
return send_from_directory(os.path.dirname(frame_file),
|
|
|
|
os.path.basename(frame_file))
|
|
|
|
|
2019-07-15 14:12:00 +02:00
|
|
|
|
2019-03-06 02:01:17 +01:00
|
|
|
@camera.route('/camera/stream', methods=['GET'])
|
2019-07-15 14:12:00 +02:00
|
|
|
@authenticate()
|
2019-03-06 02:01:17 +01:00
|
|
|
def get_default_stream_feed():
|
|
|
|
return Response(video_feed(),
|
|
|
|
mimetype='multipart/x-mixed-replace; boundary=frame')
|
|
|
|
|
2019-07-15 14:12:00 +02:00
|
|
|
|
2019-03-06 02:01:17 +01:00
|
|
|
@camera.route('/camera/<device_id>/stream', methods=['GET'])
|
2019-07-15 14:12:00 +02:00
|
|
|
@authenticate()
|
2019-03-06 02:01:17 +01:00
|
|
|
def get_stream_feed(device_id):
|
|
|
|
return Response(video_feed(device_id),
|
|
|
|
mimetype='multipart/x-mixed-replace; boundary=frame')
|
|
|
|
|
|
|
|
|
|
|
|
# vim:sw=4:ts=4:et:
|