--- trunk/webthumb 2008/02/06 19:48:56 60 +++ trunk/webthumb 2008/02/06 23:59:09 65 @@ -23,20 +23,31 @@ # HEAD (part or LWP perl library, it can be commented out) # nc (netcat, to simulate web server) # xwininfo (standard part of X-clients) -# xwit (not so standard command, but very useful) # import (part of ImageMagick package) +# xdotool (much more useful than xwit for this purpose) # # It will create snapshot of following size W=1024 H=768 +D=24 # and then resize it to (comment out to disable) #RESIZE=200x +# turn locally visible server to watch progress +DEBUG=0 +if [ ! -z "$3" ] ; then + echo "DEBUG turned on" + DEBUG=1 + D=8 +fi + +# wait for $WAIT seconds for page to load +WAIT=30 + # some configurable paths BROWSER=mozilla-firefox XSERVER=Xvfb -XWIT=xwit URL=$1 FILE=${2:-screenshot.jpg} @@ -44,13 +55,15 @@ PROFILE_DIR=`mktemp -d` PORT=8888 +LOCAL_DISPLAY=$DISPLAY + if [ -z "$URL" ] ; then echo "usage: $0 http://url.to.capture [screenshot.jpg]" exit 1 fi -if [ -z "`which $XWIT`" ] ; then - echo "$0 really need $XWIT to operate. please install it." +if [ -z "`which xdotool`" ] ; then + echo "$0 need xdotool from http://www.semicomplete.com/blog/projects/xdotool/" exit 1 fi @@ -59,6 +72,12 @@ exit 1 fi +while netstat -ln | grep ":$PORT " >/dev/null ; do + PORT=`expr $PORT + 1` +done + +echo "### using port $PORT" + echo -n "testing URL $URL " if HEAD $URL >/dev/null ; then echo "ok" @@ -67,24 +86,41 @@ exit 1 fi -echo "starting X server $XSERVER" +DISPLAY_PORT=6042 + +while netstat -ln | grep ":$DISPLAY_PORT " >/dev/null ; do + DISPLAY_PORT=`expr $DISPLAY_PORT + 1` +done + +DISPLAY=:`expr $DISPLAY_PORT - 6000` -export DISPLAY=:42 +echo "using DISPLAY=$DISPLAY" -$XSERVER -ac -screen 0 ${W}x${H}x24 $DISPLAY & -# debug server -#Xnest -display :0 -ac -geometry ${W}x${H} -depth 24 $DISPLAY & +if [ "$DEBUG" == 1 ] ; then + echo "using locally visible debug server on $LOCAL_DISPLAY" + DISPLAY=$LOCAL_DISPLAY Xephyr -ac -screen ${W}x${H}x${D} $DISPLAY 2>/dev/null & +else + echo "starting $XSERVER" + $XSERVER -ac -screen 0 ${W}x${H}x${D} $DISPLAY 2>/dev/null & +fi +if [ -z "$!" ] ; then + echo "ABORT: can't start X server!" + exit +fi XSERVER_PID=$! -echo "using pid $xserver_pid for X server" + +echo "X server pid $XSERVER_PID" function kill_x_server() { - kill $BROWSER_PID + echo "Killing server $XSERVER_PID" kill $XSERVER_PID rm -f $FRAMESET rm -fr $PROFILE_DIR + trap '' EXIT + exit 1 } -trap 'echo "QUIT!" >&2; kill_x_server; exit 1' INT QUIT TERM SEGV +trap 'kill_x_server' INT QUIT TERM SEGV EXIT # create frameset to load site and after site is loaded trigger this script cat > $FRAMESET </dev/null | grep Success echo "launching browser $BROWSER with $URL" -$BROWSER -P Screenshot -width $W -height $H $FRAMESET & +$BROWSER -P Screenshot -width $W -height $H -safemode $FRAMESET 2>/dev/null & BROWSER_PID=$! -echo "staring web server (wait for page to load)" +function kill_browser() { + echo "Killing browser $BROWSER_PID" + kill $BROWSER_PID + echo "Killing server $XSERVER_PID" + kill $XSERVER_PID + rm -f $FRAMESET + rm -fr $PROFILE_DIR + trap '' EXIT + exit 1 +} +trap 'kill_browser' INT QUIT TERM SEGV EXIT -# there is hard-coded limit here: -# we will wait 60sec for page to load and render +function ping_browser() { + echo -n "ping browser" + while ! ( $BROWSER -remote "ping();" 2>&1 ) >/dev/null ; do + RID=`xdotool search Restore 2>/dev/null` + if [ ! -z "$RID" ] ; then + echo -n "Esc" + xdotool focus $RID + xdotool key Escape + sleep 1 + fi + echo -n "." + sleep 1 + done + echo " OK" +} -echo -e "HTTP/1.0 304 Not modified\r\n\r\n" | nc -l -w 60 -p $PORT >/dev/null +ping_browser # get Mozilla Firefox window id (for resize) WINDOW_ID=`xwininfo -display $DISPLAY -root -tree | grep gecko | cut -d\" -f1 | sort -n | head -1` @@ -122,22 +181,25 @@ if [ -z "$WINDOW_ID" ] ; then echo "can't find window with name 'Mozilla Firefox'" exit 1 +else + echo "working on firefox window $WINDOW_ID" fi -# move window to foreground -$XWIT -display $DISPLAY -id $WINDOW_ID -pop +xdotool search firefox -echo "resizing window $WINDOW_ID to maximum size" -$XWIT -display $DISPLAY -id $WINDOW_ID -move 0 0 -$XWIT -display $DISPLAY -id $WINDOW_ID -resize $W $H +xdotool focus $WINDOW_ID +xdotool key F11 +ping_browser -echo -n "wating for browser ping..." -while ! ( $BROWSER -remote "ping();" 2>&1 ) >/dev/null ; do - echo -n "." - sleep 1 -done -echo +$BROWSER -remote "openURL($FRAMESET)" 2>/dev/null + +echo "waiting for on_load event from browser $BROWSER_PID for ${WAIT}s" + +# there is hard-coded limit here: +# we will wait $WAIT sec for page to load and render + +echo -e "HTTP/1.0 304 Not modified\r\n\r\n" | nc -l -w $WAIT -p $PORT >/dev/null || echo "Timeout after $WAIT sec!" # try to deduce inside area of window @@ -155,5 +217,7 @@ import -window $DUMP_ID $RESIZE $FILE -kill_x_server - +if [ "$DEBUG" == 1 ] ; then + echo -n "press enter to exit! " + read +fi