import xmpp import urllib, urllib2 import xmlrpclib from sso.services import BaseService from django.conf import settings class JabberService(BaseService): settings = { 'require_user': True, 'require_password': True, 'provide_login': False, 'use_auth_username': False, 'jabber_server': 'dredd.it', 'jabber_xmlrpc_url': 'http://127.0.0.1:4560', 'jabber_announce_from': 'announcebot@pleaseignore.com', 'jabber_announce_password': 'pepperllama', 'jabber_announce_endpoint': 'http://127.0.0.1:5281/message', 'jabber_announce_servers': ['pleaseignore.com'] } def exec_xmlrpc(self, func, **kwargs): """ Send a XMLRPC request """ if not hasattr(self, '_server'): self._server = xmlrpclib.Server(self.settings['jabber_xmlrpc_url']) params = {} for i in kwargs: params[i] = kwargs[i] return getattr(self._server, func)(params) def add_user(self, username, password, **kwargs): """ Add user to service """ username = username.lower() res = self.exec_xmlrpc('register', user=username, host=self.settings['jabber_server'], password=password) if res['res'] == 0: if 'character' in kwargs: self.exec_xmlrpc('set_nickname', user=username, host=self.settings['jabber_server'], nickname=kwargs['character'].name) self.exec_xmlrpc('set_vcard2', user=username, host=self.settings['jabber_server'], name='ORG', subname='ORGNAME', content=kwargs['character'].corporation.name) uid = "%s@%s" % (username.lower(), self.settings['jabber_server']) if 'user' in kwargs: self.update_groups(uid, kwargs['user'].groups.all()) return { 'username': uid, 'password': password } else: return False def delete_user(self, uid): """ Delete a user """ username, server = uid.lower().split("@") for group in self.get_user_groups(uid): self.exec_xmlrpc('srg_user_del', user=username, host=server, group=group, grouphost=server) res = self.exec_xmlrpc('unregister', user=username, host=server) if res['res'] == 0: return True else: return False def check_user(self, username): """ Check if the username exists """ if '@' in username: username, server = username.lower().split("@") else: server = self.settings['jabber_server'] res = self.exec_xmlrpc('check_account', user=username, host=server) if res['res'] == 0: return True else: return False def disable_user(self, uid): """ Disable a user """ username, server = uid.lower().split("@") res = self.exec_xmlrpc('ban_account', host=server, user=username, reason='Auth account disable') if res['res'] == 0: return True else: return False def enable_user(self, uid, password): """ Enable a user """ self.reset_password(uid, password) def reset_password(self, uid, password): """ Reset the user's password """ username, server = uid.lower().split("@") res = self.exec_xmlrpc('change_password', user=username, host=server, newpass=password) if res['res'] == 0: return True else: return False def get_group_list(self, server): srvgrp = self.exec_xmlrpc('srg_list', host=server) return [grp['id'].lower() for grp in srvgrp['groups']] def get_group_members(self, server, group): members = self.exec_xmlrpc('srg_get_members', group=group, host=server) return [x['member'].lower() for x in members['members']] def get_user_groups(self, uid): grouplist = [] username, server = uid.lower().split("@") for grp in self.get_group_list(server): if uid in self.get_group_members(server, grp): grouplist.append(grp) return grouplist def update_groups(self, uid, groups, character=None): username, server = uid.lower().split("@") current_groups = self.get_user_groups(uid) valid_groups = [] for group in groups: if not group.name in current_groups: groupname = group.name.lower().replace(' ', '-').replace('.', '') self.exec_xmlrpc('srg_create', group=groupname, host=server, name=group.name, description='', display='') self.exec_xmlrpc('srg_user_add', user=username, host=server, group=groupname, grouphost=server) if not groupname in current_groups: current_groups.append(groupname) if not groupname in valid_groups: valid_groups.append(groupname) for group in (set(current_groups) - set(valid_groups)): self.exec_xmlrpc('srg_user_del', user=username, host=server, group=group, grouphost=server) @property def authhandler(self): """ Generates the urllib2 Auth Handler for authenticated requests """ if not hasattr(self, '_authhandler'): passman = urllib2.HTTPPasswordMgrWithDefaultRealm() passman.add_password(None, self.settings['jabber_announce_endpoint'], self.settings['jabber_announce_from'], self.settings['jabber_announce_password']) self._authhandler = urllib2.HTTPBasicAuthHandler(passman) return self._authhandler def send_message(self, jid, body, subject=None, msgfrom=None): msg = xmpp.protocol.Message() if len(jid) > 1: msg.setTo('multicast') multi = msg.addChild(name='addresses', namespace='http://jabber.org/protocol/address') for j in jid: multi.addChild(name='address', attrs={'jid': j, 'type': 'bcc'}) elif len(jid) == 1: msg.setTo(jid[0]) else: return False if msgfrom: msg.setFrom(msgfrom) else: msg.setFrom(self.settings['jabber_announce_from']) msg.setType('chat') if subject: msg.setSubject(subject) msg.setBody(body) print str(msg) opener = urllib2.build_opener(self.authhandler) req = urllib2.Request(self.settings['jabber_announce_endpoint'], str(msg)) resp = opener.open(req) return resp.read().strip()[:2] == 'OK' def announce(self, server, message, subject=None, users=[], groups=[], servers=[]): dest = [] if len(servers): if 'all' in servers: dest = ['%s/announce/all-hosts/online' % self.settings['jabber_server']] else: dest = ['%s/announce/online' % server for server in servers] if len(users): for u in set(users): dest.append(u) if len(groups): for g in groups: dest.extend([x for x in self.get_group_members(server, g)]) dest = set(dest) if len(dest): return self.send_message(dest, message, subject) return False ServiceClass = 'JabberService'