someone thought it would be fun to be able view a screenshot of my computer via the web. i have a mac running os x, 10.3, and i think there are things sorta like webcams that upload screenshots periodically, but i didn't want to have an extra thing running, and i thought it would cool for the viewer to be able to activate the screenshot upon demand. of course there are privacy issues, so i never really made it live on the web, but i thought it was interesting.

there's a command line interface way off doing a screen shot, "screencapture" which you can find out a little more about by typing screenshot in a terminal window. the simplest case is "screencapture filename.pdf" where filename.pdf is the filename of the pdf you wish to produce.

mac os x comes with apache (personal web sharing) and it has php installed, but not activated. i edited /etc/httpd/httpd.conf to activate php (something i might cover elsewhere, but you can find out how on the web if you don't already know). php has a few different program execution functions, one of which is "exec". so my idea was to use php's exec to do the screencapture. that didn't work right away, because php runs from the web server, which runs as the user "www" and that user has very few priveleges, so the screencapture didn't work. i figured i could use sudo to give www the ability to execute screencapture. so i used visudo to edit /etc/sudoers config file so that www could do screencapture as my user without a password. so i did this:

sudo visudo

and added this line (assuming your user name is marysmith) in the # User privilege specification section (at the end of the file):

www ALL=(marysmith) NOPASSWD: /usr/sbin/screencapture

which means user www, on ALL machines (only the current one really, in my case) will execute as user marysmith, without a password, only the command screencapture
be aware that i don't know enough about security to know whether this is risky, so i wouldn't do it on a machine in a production environment

so then you can do something like this in a php file which the viewer accesses

exec ("/usr/bin/sudo -u marysmith /usr/sbin/screencapture screen.pdf");

and then if you want, you can convert it to a jpeg, and access it right in the php for display, os x 10.3 has something called "sips" which can do it. if you dont have 10.3, you can install imagemagick, and try using the "convert" command. here's what i did with sips

exec ("/usr/bin/sips -s format jpeg -i screen.pdf --out screen.jpg");

maybe i'll post the whole php file i made to do it later.
if you make one, you can put it in a directory in your Sites folder, and make the directory writeable by everyone so the www user can write the converted jpeg in it. so if you make a directory called "screenshots" then a user can access it like
http://youripaddressordomainnamehere/~marysmith/screenshots/yourphpfile.php


Note: Tiger (Mac OS X 10.4) has a screencapture utility with more options. There is a -t option for type, so you can set it to jpg and skip the second step. Also, note that the default type of a screencapture is PNG in 10.4, instead of PDF. So in 10.4, a php command can look like this:
exec ("/usr/bin/sudo -u marysmith /usr/sbin/screencapture -tjpg filename.jpg");
or if you want a .png
exec ("/usr/bin/sudo -u marysmith /usr/sbin/screencapture filename.png");


Addendum: Leopard (Mac OS X 10.5) has changes that make this more complicated. This from "man screencapture":
SECURITY CONSIDERATIONS
     To capture screen content while logged in via ssh, you must launch
     screencapture in the same mach bootstrap hierarchy as loginwindow:

     PID=pid of loginwindow
     sudo launchctl bsexec $PID screencapture [options]

Also, apache2 seems to be run by user _www (note the underscore) instead of www, so the /etc/sudoers file must reflect those changes. It seems like a real security risk to allow _www to sudo as root for something so broad as launchctl, but fortunately, the sudoers file can give very specific privileges, including command line arguments. These can include wild cards and certain patterns (done via POSIX fnmatch). You won't know the PID of the loginwindow ahead of time, but you might be able to use a pattern like [0-9]* to stand in for a number, or possibly [0-9]*[0-9] (assuming that the PID will always have at least two digits). Here's a possible /etc/sudoers entry:

_www ALL=(root) NOPASSWD: /bin/launchctl bsexec [0-9]* /usr/sbin/screencapture -tjpg filename.jpg

One could also create a shell script to execute the above command, and then give sudo for the created script only, with no command line arguments.

with the sudoers line above, php code to get a screencapture of user marysmith when that user is logged in might be:
$command = "ps auxw | grep loginwindow | grep marysmith | grep -v grep | awk '{print $2}'";
$execresult = exec ($command, $pidarray);
$pid = $pidarray[0];

if (isset($pid)) {
	$command = "sudo /bin/launchctl bsexec $pid /usr/sbin/screencapture -tjpg filename.jpg";
	$execresult = exec ($command);
}

Addendum 2: wacaw
a similar launchctl bsexec command is needed to run wacaw from an ssh login or with php from apache
see this thread: http://hintsforums.macworld.com/showthread.php?p=687257
ps auxw | grep loginwindow | grep [put user name here] | grep -v grep | awk '{print $2}'
sudo /bin/launchctl bsexec [put result of above command (a number, process id) here] ./wacaw outputfilename


up