#!/bin/sh

#
# scraper2vdr helper script
# adds the possibility to create or edit scrapinfo files
# from the vdr osd via the osdserver-plugin
#

if [ "$1" != "nowrap" ]; then
    echo "$0 nowrap \"$1\""| at now
    exit
fi


# Global settings
videodir="$2"
scrapinfo="$videodir/scrapinfo"
scrap_id=0
scrap_episode=0
variante="movie"

# Some basic tests
[ -d "$videodir" ] || exit

# Some generic stuff for handling a connection
true=0
false=1

function error() {
    # Fatal error. Send quit command, close FIFO and terminate netcat
    [ "${reply2xx[0]}" != 202 ] && SendCmd Quit

    exec 3>&-
    exec 4>&-

    kill $pid

    exit 1
}

function ConnectServer() {
    # Connect to the OSDServer

    # Set up temporary fifo and open as file descriptor 3 and 4
    mkfifo --mode=700 /tmp/pipe-in$$ /tmp/pipe-out$$
    exec 3<> /tmp/pipe-in$$
    exec 4<> /tmp/pipe-out$$
    rm /tmp/pipe-in$$ /tmp/pipe-out$$

    # Connect to server using the fifo
    { 
        netcat $1 $2

        # In case of connection loss:
        echo 499 disconnected
        echo 202 Good Bye.
    } <&3 >&4 &
    pid=$!

    # Sending to the server: use >&3
    # Receive from the server: use <&4
}


function ReadReply() {
    # Read a complete server reply until 2xx return code,
    # and store replies in each category by number
    reply2xx=()
    reply3xx=()
    reply4xx=()
    reply5xx=()
    reply6xx=()

    while read -r code line <&4 ; do
        echo "< $code $line"
        # screen echo

        case $code in
            2*)     IFS=$' \t\n\r' reply2xx=($code "$line")
                    ;;
            3*)     IFS=$' \t\n\r' reply3xx=($code $line)
                    ;;
            4*)     IFS=$' \t\n\r' reply4xx=($code "$line")
                    ;;
            5*)     IFS=$' \t\n\r' reply5xx=($code "$line")
                    ;;
            6*)     IFS=$' \t\n\r' reply6xx=($code "$line")
                    ;;
        esac
        [ -n "${reply2xx[0]}" ] && break
    done

    [ -n "${reply4xx[0]}" ] && return $false
    return $true
}

function SendCmd() {
    # Send a command and read the reply

    echo "> $*"
    # screen echo

    echo "$*" >&3
    # network send

    ReadReply
}

function IsEvent() {
    # Helper to check reply for a certain event

    [ "${reply3xx[0]}" != 300 ] && return $false
    [ "${reply3xx[1]}" != "$1" ] && return $false
    [ "${reply3xx[2]}" != "$2" ] && return $false

    return $true
}


function QuoteString() {
    # Quote arbitrary string for use in '' and ""
    local str="${!1}"

    str="${str//'\'/\\\\}"
    str="${str//'\\'/\\\\}"
    # work around bash bug: double quoted '\'

    str="${str//\'/$'\\\''}"
    # This is bogus, anyone knows something better to replace ' by \' ?

    str="${str//\"/\\\"}"
    str="${str//$'\r'/\\r}"
    str="${str//$'\n'/\\n}"
    str="${str//$'\t'/\\t}"

    eval "$1=\$str"
}

function UnquoteString() {
    # Unquote string
    local str="${!1}"

    str="${str//\\r/$'\r'}"
    str="${str//\\n/$'\n'}"
    str="${str//\\t/$'\t'}"
    str="${str//\\\"/\"}"
    str="${str//\\\'/\'}"
    str="${str//\\\\/\\}"

    eval "$1=\$str"
}


# User functions
function UpdateDB() {
    svdrpsend plug scraper2vdr SCSI
    return $true
}

function ReloadOSD() {
    svdrpsend HITK recordings
    return $true
}

function GetScrapinfo() {
    if [ -f "$scrapinfo" ]; then
        variante=$(head -1 "$scrapinfo")
        scrap_id=$(cat "$scrapinfo" | grep "id" | sed s/id.=.//)
        scrap_episode=$(cat "$scrapinfo" | grep "episode" | sed s/episode.=.//)
        return $true
    fi
    return $false
}

function DeleteScrapinfo() {
    rm -f "$scrapinfo"
    UpdateDB
    return $true
}

function CreateScrapinfo() {
    [ $scrap_id -gt 0 ] || return $false
    echo "$variante"  > "$scrapinfo"
    echo "id = $scrap_id" >> "$scrapinfo"
    [ $scrap_episode -gt 0 ] && echo "episode = $scrap_episode" >> "$scrapinfo"
    UpdateDB
    return $true
}


function ShowMenu() {
    SendCmd "menu=New Menu 'Scrapinfo Edit'" || return $false
    SendCmd "menu.SetColorKeyText -yellow 'Löschen'" || return $false
    SendCmd "menu.SetColorKeyText -blue 'Hilfe'" || return $false
    SendCmd "menu.SetColumns 15" || return $false
    SendCmd "menu.EnableEvent keyMenu keyBack keyYellow keyBlue keyOk close" || return $false

    SendCmd "variante=menu.AddNew EditListItem 'Variante' movie series  -SelectName '$variante'" || return $false
    SendCmd "id=menu.AddNew EditIntItem 'ID' '$scrap_id'" || return $false
    SendCmd "episode=menu.AddNew EditIntItem 'Episode' '$scrap_episode'" || return $false

    SendCmd "menu.Show" || return $false

    while true ; do
        SendCmd "menu.SleepEvent" || return $false

        if IsEvent menu close ; then
            return $true
        fi

        if IsEvent menu keyYellow ; then
            DeleteScrapinfo || return $false
            SendCmd "Message 'Datei wurde gelöscht'" || return $false
            SendCmd "menu.SendState osEnd" || return $false
            return $true
        fi

        if IsEvent menu keyBlue ; then
            SendCmd "Message 'Wähle Film oder Serie, gib eine ID ein und bestätige OK'" || return $false
        fi

        if IsEvent menu keyOk ; then
            SendCmd "variante.GetValue -name -quoted" || return $false
            [ "${reply5xx[0]}" != 500 ] && return $false
            variante="${reply5xx[1]}"

            SendCmd "id.GetValue" || return $false
            [ "${reply5xx[0]}" != 500 ] && return $false
            scrap_id="${reply5xx[1]}"

            if [ "$variante" == "series" ]; then
               SendCmd "episode.GetValue" || return $false
               [ "${reply5xx[0]}" != 500 ] && return $false
               scrap_episode="${reply5xx[1]}"
            else
               scrap_episode=0
            fi

            CreateScrapinfo || return $false
            SendCmd "Message 'Datei wurde angelegt'" || return $false
            SendCmd "menu.SendState osEnd" || return $false
            return $true
        fi

    done
}


###############
#  Main Code  #
###############

ConnectServer localhost 2010
# Connect to the server process

ReadReply || error
# Read server welcome

SendCmd "Version 0.1" || error
# Identify to server with protocol version

GetScrapinfo
ShowMenu || error
# Do it...

SendCmd Quit
# ... and good bye

ReloadOSD
# Jump 'back' to recordings 

exec 3>&-
exec 4>&-
# close FIFOs
