[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: cron and kmessage



On Sat, Jun 24, 2006 at 07:51:58PM -0400, Kamaraju Kusumanchi wrote:
> My actual problem is that I want to display a message at specific
> times (every 0th, 30th minute of hour) on the user's screen. I
> thought I can do this with cron and kmessage.
[snip] 
> But then it does not display the dialog on the screen. Instead it sends an 
> email to the user's address with the following message
> 
> kdialog: cannot connect to X server

These days the X Window System uses a reasonably decent authentication
scheme (with a silly name), called MIT-MAGIC-COOKIES.  When a user
starts their X session, it runs xauth for them to create their session
cookie.  You can see these using the xauth command:

  $ xauth list
  myhost/unix:0  MIT-MAGIC-COOKIE-1 85b25d08e07043401010101010101010
  localhost/unix:0  MIT-MAGIC-COOKIE-1 85b25d08e07043401010101010101010

Not that I'm really worried about anyone accessing my display, but I
sanitized my cookie above with the 1010... sequence.

By default, xauth uses the file $HOME/.Xauthority to store this
information.  If your user's home directory is not on NFS, or if it is
on NFS and you are using the no_root_squash mount option, your
processes running as root will have access to that file.  You can
either add these cookies to your own Xauthority file, or you could
tell the system to use the user's xauthority file by setting the
XAUTHORITY environment variable and the DISPLAY variable in your
script, like this:

  export DISPLAY="localhost:0.0"
  export XAUTHORITY="~user/.Xauthority"
  kdialog blahblahblah...

You will, of course, need to figure out who is logged in via X.  If
you know it will always be a particular person (i.e. yourself), you
can just put that person's username hardcoded in your script, like I
did above.  Otherwise, you'll need to figure it out programmatically.
You can do that by using the w command.  If the user is logged in
through X, their terminal will show up as something like ':0' in the
output of w, so you can grep on that:

  $ w |grep ':0'
   09:06:59 up 29 min,  5 users,  load average: 0.00, 0.14, 0.19
  root     tty1     -                08:58    6:01   0.24s  0.24s -bash
  user     :0       -                08:40   ?xdm?   1:22   0.23s /bin/bash
  
Unfortunately times can also match, since it's quite common for the
sequence :0 to show up in times (like 6:01 in the line for root, which
we don't want).  We can fix that though.  Normally in the output of w,
the display is shown as :0 or :0.0 with whitespace after the zero.
So, a better pattern to match on (using egrep instead of grep) might be
this one:

  $ w |egrep ':0(.0|)\W'
  user      :0       -                08:40   ?xdm?   1:22   0.23s /bin/bash 

Now you can use a tool like awk or cut to get just the username from
that line:

  $ user=`w |egrep ':0(.0|)\W' |awk '{print $1}'`

Now you have the user's name in the variable $user.  But you can't use
the tilde trick with a variable, i.e. if $user is "user", the shell
will unfortunately not expand ~$user to the same as ~user.  You'll
need to grep the user's passwd file entry and cut it out of that, like
this:

  $ grep "^$user:" /etc/passwd | cut -d':' -f 6

Now assign that to say, $userhome:

  $ userhome=`grep "^$user:" /etc/passwd | cut -d':' -f 6`

All together, your script will look like this:

  #!/bin/sh
  user=`w |egrep ':0(.0|)\W' |awk '{print $1}'`
  userhome=`grep "^$user:" /etc/passwd | cut -d':' -f 6`
  export DISPLAY="localhost:0.0"
  export XAUTHORITY="$userhome/.Xauthority"
  kdialog blahblahblah...

If you have multiple displays (i.e. :1.0, etc.) you might need to
change your egrep pattern.  If there's anything else weird about your
system, you'll have to figure that out for yourself too... ;-)

Now, if you CAN'T access the user's cookie file for some reason
(having it on an NFS file system being the usual reason), an
alternative might be to use the wall command to write your message to
the console and all logged in terminals...  This is the usual way for
the system administrator to communicate with all logged in users.
It's a little bit annoying, because it interrupts what the user is
doing in their terminal, but that is after all the idea.  You want to
make sure they see it...  If they are doing something like editing a
file in vi, where writing to their terminals is really disruptive,
users can redwraw their terminals by pressing ^L.

-- 
Derek D. Martin
http://www.pizzashack.org/
GPG Key ID: 0x81CFE75D

Attachment: pgppZ9aoJ10TB.pgp
Description: PGP signature


Reply to: