Skip to content

Docker: Use tmux to control recording process #2796

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: trunk
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Base/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ RUN apt-get -qqy update \
libnss3-tools \
openjdk-${JRE_VERSION}-jdk-headless \
ca-certificates \
tmux \
&& rm -rf /var/lib/apt/lists/* /var/cache/apt/*

#========================================
Expand Down
66 changes: 38 additions & 28 deletions Video/video.sh
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ file_ready_max_attempts=${SE_VIDEO_FILE_READY_WAIT_ATTEMPTS:-5}
wait_uploader_shutdown_max_attempts=${SE_VIDEO_WAIT_UPLOADER_SHUTDOWN_ATTEMPTS:-5}
ts_format=${SE_LOG_TIMESTAMP_FORMAT:-"%Y-%m-%d %H:%M:%S,%3N"}
process_name="video.recorder"
tmux_session_name="video_recorder"

if [ "${SE_VIDEO_RECORD_STANDALONE}" = "true" ]; then
JQ_SESSION_ID_QUERY=".value.nodes[]?.slots[]?.session?.sessionId"
Expand Down Expand Up @@ -140,22 +141,28 @@ function exit_on_max_session_reach() {
fi
}

function stop_ffmpeg() {
while true; do
FFMPEG_PID=$(pgrep -f ffmpeg | tr '\n' ' ')
if [ -n "$FFMPEG_PID" ]; then
kill -SIGTERM $FFMPEG_PID
wait $FFMPEG_PID
fi
if ! pgrep -f ffmpeg >/dev/null; then
break
fi
sleep ${poll_interval}
function stop_all_recording() {
current_record_sessions="$(tmux list-sessions -F "#{session_name}")"
echo "$(date -u +"${ts_format}") [${process_name}] - Current recording session(s): $current_record_sessions"
for session in $current_record_sessions; do
echo "Sending 'q' (quit signal) to session: $session"
tmux send-keys -t "$session" 'q'
done
}

function stop_all_recording_and_wait() {
stop_all_recording
for session in $current_record_sessions; do
echo "Waiting for session '$session' to finish..."
while tmux has-session -t "$session" 2>/dev/null; do
sleep 1
done
echo "Session '$session' ended."
done
}

function stop_recording() {
stop_ffmpeg
stop_all_recording_and_wait
echo "$(date -u +"${ts_format}") [${process_name}] - Video recording stopped"
recorded_count=$((recorded_count + 1))
recording_started="false"
Expand All @@ -166,12 +173,11 @@ function stop_recording() {
elif [[ "${VIDEO_UPLOAD_ENABLED}" = "true" ]] && [[ -z "${UPLOAD_DESTINATION_PREFIX}" ]]; then
echo "$(date -u +"${ts_format}") [${process_name}] - Upload destination not known since UPLOAD_DESTINATION_PREFIX is not set. Continue without uploading."
fi
echo "$(date -u +"${ts_format}") [${process_name}] - Waiting for a while to record next coming session if any"
}

function check_if_ffmpeg_running() {
if pgrep -f ffmpeg >/dev/null; then
return 0
fi
function check_if_any_session_running() {
tmux list-sessions -F "#{session_name}" 2>/dev/null | grep -q . && return 0
return 1
}

Expand All @@ -193,7 +199,7 @@ function wait_for_file_integrity() {
}

function stop_if_recording_inprogress() {
if [[ "$recording_started" = "true" ]] || check_if_ffmpeg_running; then
if [[ "$recording_started" = "true" ]] || check_if_any_session_running; then
stop_recording
fi
}
Expand All @@ -206,7 +212,7 @@ function log_node_response() {

function graceful_exit() {
echo "$(date -u +"${ts_format}") [${process_name}] - Trapped SIGTERM/SIGINT/x so shutting down recorder"
stop_if_recording_inprogress
stop_all_recording_and_wait
send_exit_signal_to_uploader
wait_util_uploader_shutdown
}
Expand All @@ -218,6 +224,12 @@ function graceful_exit_force() {
exit 0
}

function get_tmux_session_unique_index() {
tmux_index=$(tmux list-sessions 2>/dev/null | grep -o "${tmux_session_name}:[0-9]*" | cut -d: -f2)
tmux_index=${tmux_index:-0}
tmux_index=$((tmux_index + 1))
}

if [ "${SE_RECORD_AUDIO,,}" = "true" ]; then
echo "$(date -u +"${ts_format}") [${process_name}] - Audio source arguments: ${SE_AUDIO_SOURCE}"
else
Expand All @@ -229,12 +241,11 @@ if [[ "${VIDEO_UPLOAD_ENABLED}" != "true" ]] && [[ "${VIDEO_FILE_NAME}" != "auto
wait_for_display
video_file="$VIDEO_FOLDER/$VIDEO_FILE_NAME"
# exec replaces the video.sh process with ffmpeg, this makes easier to pass the process termination signal
ffmpeg -hide_banner -loglevel warning -flags low_delay -threads 2 -fflags nobuffer+genpts -strict experimental -y -f x11grab \
-video_size ${VIDEO_SIZE} -r ${FRAME_RATE} -i ${DISPLAY} ${SE_AUDIO_SOURCE} -codec:v ${CODEC} ${PRESET} -pix_fmt yuv420p "$video_file" &
FFMPEG_PID=$!
if ps -p $FFMPEG_PID >/dev/null; then
wait $FFMPEG_PID
fi
get_tmux_session_unique_index
tmux new-session -d -s ${tmux_session_name}${tmux_index} "ffmpeg -hide_banner -loglevel warning -flags low_delay -threads 2 -fflags nobuffer+genpts -strict experimental -y -f x11grab -video_size ${VIDEO_SIZE} -r ${FRAME_RATE} -i ${DISPLAY} ${SE_AUDIO_SOURCE} -codec:v ${CODEC} ${PRESET} -pix_fmt yuv420p \"$video_file\""
while tmux has-session -t "${tmux_session_name}${tmux_index}" 2>/dev/null; do
sleep 5
done

else
trap graceful_exit_force SIGTERM SIGINT EXIT
Expand Down Expand Up @@ -263,10 +274,9 @@ else
log_node_response
video_file="${VIDEO_FOLDER}/$video_file_name"
echo "$(date -u +"${ts_format}") [${process_name}] - Starting to record video"
ffmpeg -hide_banner -loglevel warning -flags low_delay -threads 2 -fflags nobuffer+genpts -strict experimental -y -f x11grab \
-video_size ${VIDEO_SIZE} -r ${FRAME_RATE} -i ${DISPLAY} ${SE_AUDIO_SOURCE} -codec:v ${CODEC} ${PRESET} -pix_fmt yuv420p "$video_file" &
FFMPEG_PID=$!
if ps -p $FFMPEG_PID >/dev/null; then
get_tmux_session_unique_index
tmux new-session -d -s ${tmux_session_name}${tmux_index} "ffmpeg -hide_banner -loglevel warning -flags low_delay -threads 2 -fflags nobuffer+genpts -strict experimental -y -f x11grab -video_size ${VIDEO_SIZE} -r ${FRAME_RATE} -i ${DISPLAY} ${SE_AUDIO_SOURCE} -codec:v ${CODEC} ${PRESET} -pix_fmt yuv420p \"$video_file\""
if tmux has-session -t ${tmux_session_name}${tmux_index} 2>/dev/null; then
recording_started="true"
prev_session_id=$session_id
fi
Expand Down
Loading