366 lines · 9.6 KB · Shell
RawDownload
#!/usr/bin/env bash if [ "${BASH_SOURCE[0]}" -ef "$0" ]then    echo "This script should not be directly executed!"    exit 1fi # A declaration of parameters and their default valuesdeclare -A ARGS=(    ["profile"]=zutty    ["step"]=no          # N.B.: --step=new will only stop at new snaps!    ["update-sig"]=no    ["ci-mode"]=no    ["debug"]=no) # Include argument handlersource "testargs.sh" PROFILE=${ARGS["profile"]}STEP_MODE=${ARGS["step"]}UPDATE_SIGNATURE=${ARGS["update-sig"]}if [ ${PROFILE} == "zutty" ] ; then    VERIFY_SNAPS=yeselse    VERIFY_SNAPS=optional    IMAGE_DIFF_TO=zuttyfiif [ ${ARGS["ci-mode"]} == "yes" ] ; then    STEP_MODE=no    UPDATE_SIGNATURE=no    EXIT_ON_FAILURE=yeselse    EXIT_ON_FAILURE=nofiif [ ${ARGS["debug"]} == "yes" ] ; then    DEBUG=yeselse    DEBUG=nofi PLATFORM=$(uname -s) EXIT_CODE=0 export TEST_NAME=$(basename -s .sh "$0") export RED="\\e[1;31m"export GREEN="\\e[1;32m"export YELLOW="\\e[1;33m"export WHITE="\\e[1;37m"export DFLT="\\e[0;39m"export ERASE_PROMPT="\\eM\\e[J" function print_error {    printf "${RED}ERROR: $@${DFLT}\n"} function CHECK_DEPS {    TOOLS="$@"; shift    MISSING=0    for t in ${TOOLS} ; do        which $t >/dev/null        if [ $? -gt 0 ] ; then            print_error "Missing dependency: $t"            MISSING=1        fi    done    if [ $MISSING -gt 0 ] ; then        exit 1    fi} function CHECK_FILES {    FILES="$@"; shift    MISSING=0    for f in ${FILES} ; do        if [ ! -f "$f" ] ; then            print_error "Missing file: $f"            MISSING=1        fi    done    if [ $MISSING -gt 0 ] ; then        exit 1    fi} function CHECK_EXE {    FILES="$@"; shift    MISSING=0    for f in ${FILES} ; do        if [ ! -x "$f" ] ; then            print_error "Missing executable: $f"            MISSING=1        fi    done    if [ $MISSING -gt 0 ] ; then        exit 1    fi} if [ ! -f "profiles/${PROFILE}.sh" ] ; then    print_error "Could not load profile: ${PROFILE}"    echo -n "Available profiles:"    for p in $(ls profiles/*.sh) ; do        echo -n " $(basename -s .sh $p)"    done    echo    exit 1fisource "profiles/${PROFILE}.sh"echo "Running test: ${TEST_NAME} with profile: ${PROFILE}"[ -n "${UUT_VERSION}" ] && echo "UUT version: ${UUT_VERSION}" export TEST_LOG="$(pwd)/output/${PROFILE}/${TEST_NAME}.log"export UUT_LOG="$(pwd)/output/${PROFILE}/${TEST_NAME}.uut.log"export UUT_SNAP="$(pwd)/output/${PROFILE}" export TEST_COUNT=0export NRES_COUNT=0export FAIL_COUNT=0 CHECK_DEPS convert compare identify mogrify xrdb xvkbd wmctrlmkdir -p $(dirname ${UUT_LOG})mkdir -p ${UUT_SNAP} CON_PID=$(ps -p $$ -o ppid=)CON_PID=$(ps -p ${CON_PID} -o ppid=)CON_WID=$(wmctrl -lp | grep ${CON_PID} | awk '{print $1}')if [ -z "${CON_WID}" ] ; then    echo "Console pid: ${CON_PID}"    printf "        ${YELLOW}wid not found, prompts won't focus console${DFLT}\n"else    echo "Console pid: ${CON_PID} wid: ${CON_WID}"fi # Add path to installed dependencies, if anyexport PATH="$(pwd)/deps/bin":$PATH # Remove any permanent configuration that could change how Zutty looks/behaves:[ ${PROFILE} == "zutty" ] && [ -f ${HOME}/.Xresources ] && xrdb -remove # execute UUT and store its pid${UUT_EXE} ${UUT_ARGS} >${UUT_LOG} 2>&1 &PID=$!echo "UUT pid: ${PID}"echo "    log file: ${UUT_LOG}"echo "    snap dir: ${UUT_SNAP}" if [ ! -z ${UUT_PID_FROM_NAME} ] ; then    sleep 0.5    PID=$(pidof ${UUT_PID_FROM_NAME})    echo "UUT pid: ${PID}"fi # wait until window opens and grab its X window idWID=''while true ; do    if [[ -z "$(ps -p ${PID} -o pid=)" ]] ; then        echo "UUT process ${PID} gone, aborting."        exit 1    fi    WID=$(wmctrl -lp | grep ${PID} | awk '{print $1}')    [[ -z "${WID}" ]] || breakdoneecho "UUT X window id: ${WID}" # focus the windowwmctrl -ia "${WID}"# set it to float (this is i3 specific):which i3-msg >/dev/null && i3-msg floating enable >/dev/null; function COUNT_PASS {    TEST_COUNT=$((TEST_COUNT + 1))    echo -n "$(test_counters)"} function COUNT_FAIL {    TEST_COUNT=$((TEST_COUNT + 1))    FAIL_COUNT=$((FAIL_COUNT + 1))    echo -n "$(test_counters)"} function COUNT_NRES {    TEST_COUNT=$((TEST_COUNT + 1))    NRES_COUNT=$((NRES_COUNT + 1))    echo -n "$(test_counters)"} function test_counters {    echo "(${TEST_COUNT}/${NRES_COUNT}/${FAIL_COUNT}) "} function FINISH_TEST {    echo "Total tests: ${TEST_COUNT}  No result: ${NRES_COUNT}  Failed: ${FAIL_COUNT}"    # display process statistics    if [ "${PLATFORM}" == "Linux" ] ; then        ps -p ${PID} -o pid,vsz,rss,trs,sz,time,maj_flt,min_flt,args \            | tee -a ${TEST_LOG}        pmap -x ${PID} >> ${TEST_LOG}        echo "Process memory map appended to ${TEST_LOG}"    else        ps -p ${PID} -o pid,vsz,rss,time,args | tee -a ${TEST_LOG}    fi     trap - EXIT    kill "${PID}"    [ ${PROFILE} == "zutty" ] && [ -f ${HOME}/.Xresources ] && \        xrdb ${HOME}/.Xresources    exit ${EXIT_CODE}} trap FINISH_TEST EXIT trap "exit 1" SIGINT function check_uut {    if [ $(wmctrl -lp | grep ${WID} | wc -l) -eq 0 ] ; then        # If IN was interrupted, Return key might have gotten stuck...        LANG=C xvkbd -window root -no-jump-pointer \            -text "\{-Return}\D3\{-Return}\D3" 2>/dev/null        echo "UUT window gone, exiting"        echo "---------- LOG TAIL ----------"        tail ${UUT_LOG}         trap - EXIT        [ ${PROFILE} == "zutty" ] && [ -f ${HOME}/.Xresources ] && \            xrdb ${HOME}/.Xresources        exit 1    fi} function IN {    local in="$1"; shift    str=$(echo "$in" | sed 's|\\r|\\D3\\{+Return}\\D3\\{-Return}|');    check_uut    LANG=C xvkbd -window ${WID} -no-jump-pointer -delay 50 \        -text "${str}\\D3" 2>&1 | \        grep -v "Mode_switch not available as a modifier" | \        grep -v "AltGr may not work correctly"} function FOCUS_CONSOLE {    if [ ! -z "${CON_WID}" ] ; then        # focus the console window        # for some reason, a simple wmctrl -ia does not work;        # it selects the window but keyboard focus is not active.        LANG=C xvkbd -window ${CON_WID} -no-back-pointer \              -text "\{+Control_L}\D1\{-Control_L}\D1" >/dev/null 2>&1    fi} function do_update_sig {    local name="$1"; shift    local newsig="$1"; shift    sed -i -e "s/SNAP ${name} .*$/SNAP ${name} ${newsig}/" "$(basename $0)"    echo "${name}: signature updated to ${newsig}"} function update_sig {    case ${UPDATE_SIGNATURE} in        all)            do_update_sig "$@"            ;;        yes)            FOCUS_CONSOLE            read -p "Update signature: [y]es / [N]o / [a]ll ? " ans            printf "${ERASE_PROMPT}"            case $ans in                [aA]* ) export UPDATE_SIGNATURE=all; do_update_sig "$@" ;;                [yY]* ) do_update_sig "$@" ;;                * ) ;;            esac            ;;        *)            ;;    esac} function step_prompt {    FOCUS_CONSOLE    read -p "[S]tep / [N]ew only / [C]ontinue / [Q]uit (s/n/c/q) ? " ans    printf "${ERASE_PROMPT}"    case $ans in        [sS]* ) STEP_MODE=yes ;;        [nN]* ) STEP_MODE=new ;;        [cC]* ) STEP_MODE=no ;;        [qQ]* ) exit ;;        * ) ;;    esac} function SNAP {    local name="$1"; shift    local refsig="$1"; shift    local imgfile=${UUT_SNAP}/${name}.png    check_uut    xwd -silent -nobdrs -id ${WID} | convert xwd:- png:- > ${imgfile}    mogrify -strip -taint -compress Lossless ${imgfile}     case ${VERIFY_SNAPS} in        yes)            sig=$(identify -verbose ${imgfile} | grep signature | \                      awk '{print $2}' | cut -c -32)            if [ -z "${refsig}" ] ; then                COUNT_NRES                printf "${name}: ${YELLOW}NEW${DFLT} ${sig}\n"                if [ ${STEP_MODE} == "new" ] ; then                    step_prompt                fi            elif [ "${sig}" == "${refsig}" ] ; then                COUNT_PASS                printf "${name}: ${GREEN}OK${DFLT}\n"            else                COUNT_FAIL                printf "${name}: ${RED}FAIL${DFLT} sig ${sig} ref ${refsig}\n"                update_sig ${name} ${sig}                EXIT_CODE=1                if [ ${EXIT_ON_FAILURE} == "yes" ] ; then                    exit                fi            fi            ;;        optional)            sig=$(identify -verbose ${imgfile} | grep signature | \                      awk '{print $2}' | cut -c -32)            imgerr=${UUT_SNAP}/${name}.error.png            if [ "${sig}" == "${refsig}" ] ; then                rm -f ${imgerr}                COUNT_PASS                printf "${name}: ${GREEN}MATCH${DFLT}\n"            else                COUNT_NRES                if [ ! -z ${IMAGE_DIFF_TO} ] ; then                    imgref="$(pwd)/output/${IMAGE_DIFF_TO}/${name}.png"                    rm -f ${imgerr}                    AE=$(compare ${imgref} ${imgfile} -metric AE ${imgerr} 2>&1)                    if [ $? -eq 2 ] ; then                        printf "${name}: ${WHITE}DONE${DFLT} (different dimensions)\n"                    else                        printf "${name}: ${WHITE}DONE${DFLT} (AE=${AE})\n"                    fi                else                    printf "${name}: ${WHITE}DONE${DFLT}\n"                fi            fi            ;;        *)            COUNT_NRES            printf "${name}: ${WHITE}DONE${DFLT}\n"            ;;    esac     if [ ${STEP_MODE} == "yes" ] ; then        step_prompt    fi} function WAIT_FOR_DOT_COMPLETE {    while true ; do        [[ -f .complete ]] && break        sleep 0.1    done    rm -f .complete}

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t