From 04ab079db36ae8162ea6e2a30e3507b23ab196c8 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Kristian=20Kr=C3=A6mmer=20Nielsen?= Date: Mon, 3 Apr 2017 13:58:32 +0200 Subject: [PATCH] New release Moved record config to seperate file Tuned timeouts Picking better stream bandwidth for recording Fix resync on lost segments --- monitor-dai.sh | 86 ++++++++++++++++++++++++++++-------------------- record-config.sh | 11 +++++++ 2 files changed, 61 insertions(+), 36 deletions(-) create mode 100644 record-config.sh diff --git a/monitor-dai.sh b/monitor-dai.sh index c89c467..6f55296 100755 --- a/monitor-dai.sh +++ b/monitor-dai.sh @@ -26,7 +26,7 @@ # monitor-dai.sh # -BASIC_CURL_PARAMS="--connect-timeout 10 --location --max-time 60 -Ss" +BASIC_CURL_PARAMS="--connect-timeout 15 --location -Ss" SCRIPT_NAME=$(basename "$0") DATE_BSD="date -r " @@ -41,8 +41,7 @@ fi # Used as default 10 seconds pause before retrying TARGET_DURATION=10 -# No adblocks to record -RECORD_AD_BLOCKS=3 +source "$(dirname $0)/record-config.sh" || fatal "Missing record-config.sh" # Very limited function to resolve relative url function resolveRelativeURL() { @@ -80,15 +79,22 @@ function fatal() { # Extract first stream from HLS Master-Playlist function resolveFirstStream() { local hls="$1" + local bandwidth=-1 TMPFILE=$(mktemp) || fatal "Can not write tmp-file" - url=$(curl $BASIC_CURL_PARAMS -o "$TMPFILE" "$hls" -w "%{url_effective}") + url=$(curl $BASIC_CURL_PARAMS --max-time 20 -o "$TMPFILE" "$hls" -w "%{url_effective}") if [ $? -eq 0 ]; then while IFS="" read line; do - # First none comment is first element in playlist => we will use that stream - re="^[^#].*$" + # Select proper bandwidth + re="^#EXT-X-STREAM-INF[:,]BANDWIDTH=([0-9]+)(,|$)" if [[ "$line" =~ $re ]]; then - echo $(resolveRelativeURL "$line" "$url") - break + bandwidth="${BASH_REMATCH[1]}" + # First none comment is first element in playlist => we will use that stream + elif [[ "$bandwidth" -ne -1 && "$bandwidth" -lt "$RECORD_MAX_BANDWIDTH" ]]; then + re="^[^#].*$" + if [[ "$line" =~ $re ]]; then + echo $(resolveRelativeURL "$line" "$url") + break + fi fi done <"$TMPFILE" else @@ -117,7 +123,7 @@ function monitorStream() { local syncMode=-1 # (-1=get first, x=saw last at, 0=synched) In syncmode we try to request every second until we see a change to get a more precise time sync local stream_time="" # unknown - echo >&2 "$pretty_time: INFO: Started monitoring using: $stream" + echo >&2 "INFO: Started monitoring using: $stream" while true; do starttime=$(date +%s) @@ -125,10 +131,11 @@ function monitorStream() { # Set time to real time first request if [ -z "$stream_time" ]; then + syncMode=-1 if [ -n "$streamDelay" ]; then stream_time=$(($starttime - $streamDelay)) pretty_time=$($DATE${stream_time%.*} +"%Y-%m-%d %H:%M:%S") - echo >&2 "NOTICE: Using time-offset of -${streamDelay}s. Stream time is $pretty_time, real time is $(date ${realtime} +"%Y-%m-%d %H:%M:%S")" + echo >&2 "NOTICE: Using time-offset of -${streamDelay}s. Stream time is $pretty_time, real time is $($DATE${starttime} +"%Y-%m-%d %H:%M:%S")" else stream_time="$starttime" pretty_time=$($DATE${stream_time%.*} +"%Y-%m-%d %H:%M:%S") @@ -137,7 +144,7 @@ function monitorStream() { fi TMPFILE=$(mktemp) || fatal "Can not write tmp-file" - curl $BASIC_CURL_PARAMS -o "$TMPFILE" "$stream" + curl $BASIC_CURL_PARAMS --max-time 25 -o "$TMPFILE" "$stream" if [ $? -eq 0 ]; then while IFS="" read line; do @@ -160,7 +167,7 @@ function monitorStream() { if [[ $curSeq -ne -1 ]]; then # we know media sequence if [[ $curSeq -ge $nextSeq ]]; then # later sequence than we need if [[ $doRecord -eq 1 ]]; then - saveStreamBit "$stream" "$tags" "$stream_time" "$recordFolder" + saveStreamBit "$stream" "$tags" "$stream_time" "$recordFolder" & fi lastUsedSegment="$tags" lastUsedStreamTime="$stream_time" @@ -170,8 +177,15 @@ function monitorStream() { pretty_time=$($DATE${stream_time%.*} +"%Y-%m-%d %H:%M:%S") if [[ $curSeq -ne $nextSeq ]]; then echo >&2 "$pretty_time: WARN: Lost segments ($curSeq > $nextSeq)." - stream_time= + stream_time="" syncMode=-1 + curSeq=-1 + doRecord=0 + doStopRecord=0 + nextSeq=-1 + tags="" + mode="UNKNOWN" + break fi #echo >&2 "$pretty_time: Current mode length: $curLength" nextSeq=$(($curSeq + 1)) @@ -229,21 +243,21 @@ function monitorStream() { echo >&2 "$pretty_time: INFO: Seeing CUE-OUT (Ad block start) of duration: $value" if [ "$mode" == "ADBLOCK" ]; then echo >&2 "$pretty_time: ERROR: Already in ad block - extra cue-out after $curLength" - #else - # echo >&2 "$pretty_time: INFO: Ad-block started after $curLength seconds" - fi - mode="ADBLOCK" - expectedAdLength=$value - curLength=0 - if [ "$RECORD_AD_BLOCKS" -gt 0 ]; then - if [ -z "$lastUsedSegment" ]; then - echo >&2 "$pretty_time: INFO: Skipping recording since we did not see start of it." - else - RECORD_AD_BLOCKS=$(($RECORD_AD_BLOCKS - 1)) - echo >&2 "$pretty_time: INFO: Recording this adblock ($RECORD_AD_BLOCKS left)." - saveStreamBit "$stream" "$lastUsedSegment" "$lastUsedStreamTime" "$recordFolder" - doRecord=1 - doStopRecord=0 + else + #echo >&2 "$pretty_time: INFO: Ad-block started after $curLength seconds" + mode="ADBLOCK" + expectedAdLength=$value + curLength=0 + if [ "$RECORD_AD_BLOCKS" -gt 0 ]; then + if [ -z "$lastUsedSegment" ]; then + echo >&2 "$pretty_time: INFO: Skipping recording since we did not see start of it." + else + RECORD_AD_BLOCKS=$(($RECORD_AD_BLOCKS - 1)) + echo >&2 "$pretty_time: INFO: Recording this adblock ($RECORD_AD_BLOCKS left)." + saveStreamBit "$stream" "$lastUsedSegment" "$lastUsedStreamTime" "$recordFolder" & + doRecord=1 + doStopRecord=0 + fi fi fi elif [ "$tag" == "EXT-X-CUE-IN" ]; then @@ -253,15 +267,15 @@ function monitorStream() { if [ "$expectedAdLength" != "$curLength" ]; then echo >&2 "$pretty_time: WARN: Block was not the length expected ($curLength <> $expectedAdLength)" fi + if [ "$doRecord" == "1" ]; then + echo >&2 "$pretty_time: INFO: Stopping recording." + doStopRecord=1 + fi + curLength=0 elif [ "$mode" == "LIVE" ]; then echo >&2 "$pretty_time: ERROR: Extra CUE-IN outside Ad-block after $curLength" fi mode="LIVE" - curLength=0 - if [ "$doRecord" == "1" ]; then - echo >&2 "$pretty_time: INFO: Stopping recording." - doStopRecord=1 - fi fi fi fi @@ -332,13 +346,13 @@ function saveStreamBit() { # Fetch key if needed if [[ -n "$keyURI" ]]; then keyURI=$(resolveRelativeURL "$keyURI" "$streamURI") - key=$(curl $BASIC_CURL_PARAMS "$keyURI" | hexdump -v -e '/1 "%02X"') + key=$(curl $BASIC_CURL_PARAMS --max-time 480 "$keyURI" | hexdump -v -e '/1 "%02X"') # Decrypt on the fly - curl $BASIC_CURL_PARAMS "$uri" | \ + curl $BASIC_CURL_PARAMS --max-time 480 "$uri" | \ openssl aes-128-cbc -d -K "$key" -iv "$keyIV" -nosalt -out "$output" else # Fetch stream to file - curl $BASIC_CURL_PARAMS -o "$output" "$uri" + curl $BASIC_CURL_PARAMS --max-time 480 -o "$output" "$uri" fi else re="^#EXT-X-KEY:METHOD=(AES-128|NONE)(,URI=\"([^\"]*)\",IV=0x([0-9A-F]+))?" diff --git a/record-config.sh b/record-config.sh new file mode 100644 index 0000000..779a67b --- /dev/null +++ b/record-config.sh @@ -0,0 +1,11 @@ +#!/usr/bin/env bash +# ========================================== +# Configuration file for DAI monitor +# ========================================== + +# Should we record a number of ad blocks? +RECORD_AD_BLOCKS=3 + +# Max bandwidth to select +RECORD_MAX_BANDWIDTH=600000 + -- 2.52.0