[JDEV] Admin Rights

DJ Adams dj.adams at pobox.com
Sat Jun 9 05:42:12 CDT 2001


On Fri, Jun 08, 2001 at 04:32:49PM -0600, Todd Miller wrote:
> Is there a way to determine if a user has admin rights on the server.  I
> have written a utility to send server announcements and I want to disallow a
> user from logging in to the utility if they do not have admin rights.  The
> utility connects using the JabberCOM.DLL.

(before I start, apologies if I'm on the wrong track)

Although stpeter has answered referring to the jabber.xml config file,
I'll assume that your utility doesn't have access to this, and you want to
do it programatically (as you mention the JabberCOM library). 

It's an interesting question that (to me) has a few wider implications, 
over and above the 'how can I find out if a user has admin rights' question.

But to this question first; there are at least two approaches - try to 
discover before logging on, or try to discover after logging on.

The latter is easy if a little crass - log on and try to do something
that requires admin rights (e.g. an iq:admin 'who' query) and check for error
messages. It's also not that neat either, as - even though you don't have to 
end presence, to avoid an avalanche of offline messages that the user isn't
going to get a chance to deal with - having already logged on, it's too late
- we're already logged on, which was to be avoided. On the whole, not good.

The former is a bit more interesting. Can we make a query before logging 
on to find out about admin rights? Not really, as the only query namespaces
that are honoured before a session is started on a stream are the iq:auth and
iq:register namespaces. All other elements are buffered until authentication
has taken place. But consider the iq-get request made in the iq:auth namespace.
This (optional) step allows the client to discover the authentication methods
supported for that user:

SEND: <iq type='get'>
        <query xmlns='jabber:iq:auth'>
          <username>qmacro</username>
        </query>
      </iq>

RECV: <iq type='result'>
        <query xmlns='jabber:iq:auth'>
          <username>qmacro</username>
          <password/>
          <digest/>
          <sequence>123</sequence><token>ABCDEF12</token>
          <resource/>
        </query>
      </iq>

JSM modules can register for the iq:auth namespace and will tack on 
tags to the result for an iq-get announcing their readiness to handle
an authorisation check via an iq-set. The <resource/> tag is tacked
on the end too, which got me thinking. Taking advantage of the current
lack of optional/mandatory determination in the result tags, would it
be possible to write another module that would tack on extra information?

I'm certainly not suggesting this is the right solution at all - I'm 
ready to be shot down in flames for trying this out, but I just did it
as a learning exercise. I created a new JSM module mod_dj_admin.c :

#include <jsm.h>

mreturn mod_dj_admin_yip(mapi m, void *arg)
{
  if(jpacket_subtype(m->packet) == JPACKET__GET)
  {
    if(js_admin(m->user,ADMIN_READ))
      xmlnode_insert_tag(m->packet->iq,"read");
    if(js_admin(m->user,ADMIN_WRITE))
      xmlnode_insert_tag(m->packet->iq,"write");
  }
  return M_PASS;
}

void mod_dj_admin(jsmi si)
{
  js_mapi_register(si,e_AUTH, mod_dj_admin_yip, NULL);
}

and added it into JSM's <load/> area, below mod_auth_0k. 

Now a 

SEND: <iq type='get'>
        <query xmlns='jabber:iq:auth'>
          <username>qmacro</username>
        </query>
      </iq>

will return extra tags <write/> and / or <read/> depending on the admin
rights of the username in the query, something like this:

RECV: <iq type='result'>
        <query xmlns='jabber:iq:auth'>
          <username>qmacro</username>
          <password/>
          <digest/>
          <sequence>123</sequence><token>ABCDEF12</token>
          <read/>
          <write/>
          <resource/>
        </query>
      </iq>

This way, a client could determine admin rights before deciding whether 
to go ahead and authenticate. 

Anyway, the other side to this question comes from other systems that I'm 
more familiar with: SAP, for example, has a mode where you can prevent anyone
logging in except admin users (e.g. SAP* or DDIC). I'm wondering whether this
would be a useful feature for Jabber too, as more and more services are 
added and those services administered using the Jabber protocol itself, with
the ultimate goal not to have to take the server down. Of course, there's 
another part of this to be addressed - in the switchover from 'normal' mode
to 'admin' mode, there will be 'normal' users left connected, who will have
to be 'thrown off'. Anyway, I'll stop here for now, otherwise I'll start to
bore everyone to death. Has anyone else considered such 'mode switch' 
functionality?

dj
on his 4th cup of coffee this morning



More information about the JDev mailing list