diff options
Diffstat (limited to 'src/xmpppy-0.5.0rc1/doc/examples')
-rwxr-xr-x | src/xmpppy-0.5.0rc1/doc/examples/README.py | 71 | ||||
-rwxr-xr-x | src/xmpppy-0.5.0rc1/doc/examples/bot.py | 94 | ||||
-rw-r--r-- | src/xmpppy-0.5.0rc1/doc/examples/commandsbot.py | 289 | ||||
-rwxr-xr-x | src/xmpppy-0.5.0rc1/doc/examples/logger.py | 75 | ||||
-rwxr-xr-x | src/xmpppy-0.5.0rc1/doc/examples/xsend.py | 44 | ||||
-rw-r--r-- | src/xmpppy-0.5.0rc1/doc/examples/xtalk.py | 83 |
6 files changed, 656 insertions, 0 deletions
diff --git a/src/xmpppy-0.5.0rc1/doc/examples/README.py b/src/xmpppy-0.5.0rc1/doc/examples/README.py new file mode 100755 index 00000000..ae01dc62 --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/README.py @@ -0,0 +1,71 @@ +#!/usr/bin/python +# -*- coding: koi8-r -*- +from xmpp import * + +def presenceHandler(conn,presence_node): + """ Handler for playing a sound when particular contact became online """ + targetJID='node@domain.org' + if presence_node.getFrom().bareMatch(targetJID): + # play a sound + pass +def iqHandler(conn,iq_node): + """ Handler for processing some "get" query from custom namespace""" + reply=iq_node.buildReply('result') + # ... put some content into reply node + conn.send(reply) + raise NodeProcessed # This stanza is fully processed +def messageHandler(conn,mess_node): pass + +if 1: + """ + Example 1: + Connecting to specified IP address. + Connecting to port 5223 - TLS is pre-started. + Using direct connect. + """ + # Born a client + cl=Client('ejabberd.somedomain.org') + # ...connect it to SSL port directly + if not cl.connect(server=('1.2.3.4',5223)): + raise IOError('Can not connect to server.') +else: + """ + Example 2: + Connecting to server via proxy. + Assuming that servername resolves to jabber server IP. + TLS will be started automatically if available. + """ + # Born a client + cl=Client('jabberd2.somedomain.org') + # ...connect via proxy + if not cl.connect(proxy={'host':'someproxy.somedomain.org','port':'8080','user':'proxyuser','password':'proxyuserpassword'}): + raise IOError('Can not connect to server.') +# ...authorize client +if not cl.auth('jabberuser','jabberuserpassword','optional resource name'): + raise IOError('Can not auth with server.') +# ...register some handlers (if you will register them before auth they will be thrown away) +cl.RegisterHandler('presence',presenceHandler) +cl.RegisterHandler('iq',iqHandler) +cl.RegisterHandler('message',messageHandler) +# ...become available +cl.sendInitPresence() +# ...work some time +cl.Process(1) +# ...if connection is brocken - restore it +if not cl.isConnected(): cl.reconnectAndReauth() +# ...send an ASCII message +cl.send(Message('test@jabber.org','Test message')) +# ...send a national message +cl.send(Message('test@jabber.org',unicode('Проверка связи','koi8-r'))) +# ...send another national message +simplexml.ENCODING='koi8-r' +cl.send(Message('test@jabber.org','Проверка связи 2')) +# ...work some more time - collect replies +cl.Process(1) +# ...and then disconnect. +cl.disconnect() + +""" +If you have used jabberpy before you will find xmpppy very similar. +See the docs for more info about library features. +""" diff --git a/src/xmpppy-0.5.0rc1/doc/examples/bot.py b/src/xmpppy-0.5.0rc1/doc/examples/bot.py new file mode 100755 index 00000000..42636300 --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/bot.py @@ -0,0 +1,94 @@ +#!/usr/bin/python +# -*- coding: koi8-r -*- +# $Id: bot.py,v 1.2 2006/10/06 12:30:42 normanr Exp $ +import sys +import xmpp + +commands={} +i18n={'ru':{},'en':{}} +########################### user handlers start ################################## +i18n['en']['HELP']="This is example jabber bot.\nAvailable commands: %s" +def helpHandler(user,command,args,mess): + lst=commands.keys() + lst.sort() + return "HELP",', '.join(lst) + +i18n['en']['EMPTY']="%s" +i18n['en']['HOOK1']='Responce 1: %s' +def hook1Handler(user,command,args,mess): + return "HOOK1",'You requested: %s'%args + +i18n['en']['HOOK2']='Responce 2: %s' +def hook2Handler(user,command,args,mess): + return "HOOK2","hook2 called with %s"%(`(user,command,args,mess)`) + +i18n['en']['HOOK3']='Responce 3: static string' +def hook3Handler(user,command,args,mess): + return "HOOK3"*int(args) +########################### user handlers stop ################################### +############################ bot logic start ##################################### +i18n['en']["UNKNOWN COMMAND"]='Unknown command "%s". Try "help"' +i18n['en']["UNKNOWN USER"]="I do not know you. Register first." + +def messageCB(conn,mess): + text=mess.getBody() + user=mess.getFrom() + user.lang='en' # dup + if text.find(' ')+1: command,args=text.split(' ',1) + else: command,args=text,'' + cmd=command.lower() + + if commands.has_key(cmd): reply=commands[cmd](user,command,args,mess) + else: reply=("UNKNOWN COMMAND",cmd) + + if type(reply)==type(()): + key,args=reply + if i18n[user.lang].has_key(key): pat=i18n[user.lang][key] + elif i18n['en'].has_key(key): pat=i18n['en'][key] + else: pat="%s" + if type(pat)==type(''): reply=pat%args + else: reply=pat(**args) + else: + try: reply=i18n[user.lang][reply] + except KeyError: + try: reply=i18n['en'][reply] + except KeyError: pass + if reply: conn.send(xmpp.Message(mess.getFrom(),reply)) + +for i in globals().keys(): + if i[-7:]=='Handler' and i[:-7].lower()==i[:-7]: commands[i[:-7]]=globals()[i] + +############################# bot logic stop ##################################### + +def StepOn(conn): + try: + conn.Process(1) + except KeyboardInterrupt: return 0 + return 1 + +def GoOn(conn): + while StepOn(conn): pass + +if len(sys.argv)<3: + print "Usage: bot.py username@server.net password" +else: + jid=xmpp.JID(sys.argv[1]) + user,server,password=jid.getNode(),jid.getDomain(),sys.argv[2] + + conn=xmpp.Client(server)#,debug=[]) + conres=conn.connect() + if not conres: + print "Unable to connect to server %s!"%server + sys.exit(1) + if conres<>'tls': + print "Warning: unable to estabilish secure connection - TLS failed!" + authres=conn.auth(user,password) + if not authres: + print "Unable to authorize on %s - check login/password."%server + sys.exit(1) + if authres<>'sasl': + print "Warning: unable to perform SASL auth os %s. Old authentication method used!"%server + conn.RegisterHandler('message',messageCB) + conn.sendInitPresence() + print "Bot started." + GoOn(conn) diff --git a/src/xmpppy-0.5.0rc1/doc/examples/commandsbot.py b/src/xmpppy-0.5.0rc1/doc/examples/commandsbot.py new file mode 100644 index 00000000..f32c13c6 --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/commandsbot.py @@ -0,0 +1,289 @@ +#!/usr/bin/python +""" The example of using xmpppy's Ad-Hoc Commands (JEP-0050) implementation. +""" +import xmpp +from xmpp.protocol import * + +options = { + 'JID': 'circles@example.com', + 'Password': '********', +} + +class TestCommand(xmpp.commands.Command_Handler_Prototype): + """ Example class. You should read source if you wish to understate how it works. This one + actually does some calculations.""" + name = 'testcommand' + description = 'Circle calculations' + def __init__(self, jid=''): + """ Initialize some internals. Set the first request handler to self.calcTypeForm. + """ + xmpp.commands.Command_Handler_Prototype.__init__(self,jid) + self.initial = { + 'execute': self.initialForm + } + + def initialForm(self, conn, request): + """ Assign a session id and send the first form. """ + sessionid = self.getSessionID() + self.sessions[sessionid] = { + 'jid':request.getFrom(), + 'data':{'type':None} + } + + # simulate that the client sent sessionid, so calcTypeForm will be able + # to continue + request.getTag(name="command").setAttr('sessionid', sessionid) + + return self.calcTypeForm(conn, request) + + def calcTypeForm(self, conn, request): + """ Send first form to the requesting user. """ + # get the session data + sessionid = request.getTagAttr('command','sessionid') + session = self.sessions[sessionid] + + # What to do when a user sends us a response? Note, that we should always + # include 'execute', as it is a default action when requester does not send + # exact action to do (should be set to the same as 'next' or 'complete' fields) + session['actions'] = { + 'cancel': self.cancel, + 'next': self.calcTypeFormAccept, + 'execute': self.calcTypeFormAccept, + } + + # The form to send + calctypefield = xmpp.DataField( + name='calctype', + desc='Calculation Type', + value=session['data']['type'], + options=[ + ['Calculate the diameter of a circle','circlediameter'], + ['Calculate the area of a circle','circlearea'] + ], + typ='list-single', + required=1) + + # We set label attribute... seems that the xmpppy.DataField cannot do that + calctypefield.setAttr('label', 'Calculation Type') + + form = xmpp.DataForm( + title='Select type of operation', + data=[ + 'Use the combobox to select the type of calculation you would like'\ + 'to do, then click Next.', + calctypefield]) + + # Build a reply with the form + reply = request.buildReply('result') + replypayload = [ + xmpp.Node('actions', + attrs={'execute':'next'}, + payload=[xmpp.Node('next')]), + form] + reply.addChild( + name='command', + namespace=NS_COMMANDS, + attrs={ + 'node':request.getTagAttr('command','node'), + 'sessionid':sessionid, + 'status':'executing'}, + payload=replypayload) + self._owner.send(reply) # Question: self._owner or conn? + raise xmpp.NodeProcessed + + def calcTypeFormAccept(self, conn, request): + """ Load the calcType form filled in by requester, then reply with + the second form. """ + # get the session data + sessionid = request.getTagAttr('command','sessionid') + session = self.sessions[sessionid] + + # load the form + node = request.getTag(name='command').getTag(name='x',namespace=NS_DATA) + form = xmpp.DataForm(node=node) + + # retrieve the data + session['data']['type'] = form.getField('calctype').getValue() + + # send second form + return self.calcDataForm(conn, request) + + def calcDataForm(self, conn, request, notavalue=None): + """ Send a form asking for diameter. """ + # get the session data + sessionid = request.getTagAttr('command','sessionid') + session = self.sessions[sessionid] + + # set the actions taken on requester's response + session['actions'] = { + 'cancel': self.cancel, + 'prev': self.calcTypeForm, + 'next': self.calcDataFormAccept, + 'execute': self.calcDataFormAccept + } + + # create a form + radiusfield = xmpp.DataField(desc='Radius',name='radius',typ='text-single') + radiusfield.setAttr('label', 'Radius') + + form = xmpp.DataForm( + title = 'Enter the radius', + data=[ + 'Enter the radius of the circle (numbers only)', + radiusfield]) + + # build a reply stanza + reply = request.buildReply('result') + replypayload = [ + xmpp.Node('actions', + attrs={'execute':'complete'}, + payload=[xmpp.Node('complete'),xmpp.Node('prev')]), + form] + + if notavalue: + replypayload.append(xmpp.Node('note', + attrs={'type': 'warn'}, + payload=['You have to enter valid number.'])) + + reply.addChild( + name='command', + namespace=NS_COMMANDS, + attrs={ + 'node':request.getTagAttr('command','node'), + 'sessionid':request.getTagAttr('command','sessionid'), + 'status':'executing'}, + payload=replypayload) + + self._owner.send(reply) + raise xmpp.NodeProcessed + + def calcDataFormAccept(self, conn, request): + """ Load the calcType form filled in by requester, then reply with the result. """ + # get the session data + sessionid = request.getTagAttr('command','sessionid') + session = self.sessions[sessionid] + + # load the form + node = request.getTag(name='command').getTag(name='x',namespace=NS_DATA) + form = xmpp.DataForm(node=node) + + # retrieve the data; if the entered value is not a number, return to second stage + try: + value = float(form.getField('radius').getValue()) + except: + self.calcDataForm(conn, request, notavalue=True) + + # calculate the answer + from math import pi + if session['data']['type'] == 'circlearea': + result = (value**2) * pi + else: + result = 2 * value * pi + + # build the result form + form = xmpp.DataForm( + typ='result', + data=[xmpp.DataField(desc='result', name='result', value=result)]) + + # build the reply stanza + reply = request.buildReply('result') + reply.addChild( + name='command', + namespace=NS_COMMANDS, + attrs={ + 'node':request.getTagAttr('command','node'), + 'sessionid':sessionid, + 'status':'completed'}, + payload=[form]) + + self._owner.send(reply) + + # erase the data about session + del self.sessions[sessionid] + + raise xmpp.NodeProcessed + + def cancel(self, conn, request): + """ Requester canceled the session, send a short reply. """ + # get the session id + sessionid = request.getTagAttr('command','sessionid') + + # send the reply + reply = request.buildReply('result') + reply.addChild( + name='command', + namespace=NS_COMMANDS, + attrs={ + 'node':request.getTagAttr('command','node'), + 'sessionid':sessionid, + 'status':'cancelled'}) + self._owner.send(reply) + + # erase the data about session + del self.sessions[sessionid] + + raise xmpp.NodeProcessed + +class ConnectionError: pass +class AuthorizationError: pass +class NotImplemented: pass + +class Bot: + """ The main bot class. """ + + def __init__(self, JID, Password): + """ Create a new bot. Connect to the server and log in. """ + + # connect... + jid = xmpp.JID(JID) + self.connection = xmpp.Client(jid.getDomain(), debug=['always', 'browser', 'testcommand']) + + result = self.connection.connect() + + if result is None: + raise ConnectionError + + # authorize + result = self.connection.auth(jid.getNode(), Password) + + if result is None: + raise AuthorizationError + + # plugins + # disco - needed by commands + + # warning: case of "plugin" method names are important! + # to attach a command to Commands class, use .plugin() + # to attach anything to Client class, use .PlugIn() + self.disco = xmpp.browser.Browser() + self.disco.PlugIn(self.connection) + self.disco.setDiscoHandler({ + 'info': { + 'ids': [{ + 'category': 'client', + 'type': 'pc', + 'name': 'Bot' + }], + 'features': [NS_DISCO_INFO], + } + }) + + self.commands = xmpp.commands.Commands(self.disco) + self.commands.PlugIn(self.connection) + + self.command_test = TestCommand() + self.command_test.plugin(self.commands) + + # presence + self.connection.sendInitPresence(requestRoster=0) + + def loop(self): + """ Do nothing except handling new xmpp stanzas. """ + try: + while self.connection.Process(1): + pass + except KeyboardInterrupt: + pass + +bot = Bot(**options) +bot.loop() diff --git a/src/xmpppy-0.5.0rc1/doc/examples/logger.py b/src/xmpppy-0.5.0rc1/doc/examples/logger.py new file mode 100755 index 00000000..b99686c1 --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/logger.py @@ -0,0 +1,75 @@ +#!/usr/bin/python +# -*- coding: koi8-r -*- +from xmpp import * +import time,os + +#BOT=(botjid,password) +BOT=('test@penza-gsm.ru','test') +#CONF=(confjid,password) +CONF=('talks@conference.jabber.ru','') +LOGDIR='./' +PROXY={} +#PROXY={'host':'192.168.0.1','port':3128,'username':'luchs','password':'secret'} +####################################### + +def LOG(stanza,nick,text): + ts=stanza.getTimestamp() + if not ts: + ts=stanza.setTimestamp() + ts=stanza.getTimestamp() + tp=time.mktime(time.strptime(ts,'%Y%m%dT%H:%M:%S %Z'))+3600*3 + if time.localtime()[-1]: tp+=3600 + tp=time.localtime(tp) + fold=stanza.getFrom().getStripped().replace('@','%')+'_'+time.strftime("%Y.%m",tp) + day=time.strftime("%d",tp) + tm=time.strftime("%H:%M:%S",tp) + try: os.mkdir(LOGDIR+fold) + except: pass + fName='%s%s/%s.%s.html'%(LOGDIR,fold,fold,day) + try: open(fName) + except: + open(fName,'w').write("""<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> +<html xml:lang="ru-RU" lang="ru-RU" xmlns="http://www.w3.org/1999/xhtml"> + <head> + <meta content="text/html; charset=utf-8" http-equiv="content-type" /> + <title>%s logs for %s.%s.</title> + </head> + <body> +<table border="1"><tr><th>time</th><th>who</th><th>text</th></tr> +"""%(CONF[0],fold,day)) + text='<pre>%s</pre>'%text + open(fName,'a').write((u"<tr><td>%s</td><td>%s</td><td>%s</td></tr>\n"%(tm,nick,text)).encode('utf-8')) + print (u"<tr><td>%s</td><td>%s</td><td>%s</td></tr>\n"%(tm,nick,text)).encode('koi8-r','replace') +# print time.localtime(tp),nick,text + +def messageCB(sess,mess): + nick=mess.getFrom().getResource() + text=mess.getBody() + LOG(mess,nick,text) + +roster=[] +def presenceCB(sess,pres): + nick=pres.getFrom().getResource() + text='' + if pres.getType()=='unavailable': + if nick in roster: + text=nick+unicode(' покинул конференцию','koi8-r') + roster.remove(nick) + else: + if nick not in roster: + text=nick+unicode(' пришёл в конференцию','koi8-r') + roster.append(nick) + if text: LOG(pres,nick,text) + +if 1: + cl=Client(JID(BOT[0]).getDomain(),debug=[]) + cl.connect(proxy=PROXY) + cl.RegisterHandler('message',messageCB) + cl.RegisterHandler('presence',presenceCB) + cl.auth(JID(BOT[0]).getNode(),BOT[1]) + p=Presence(to='%s/logger'%CONF[0]) + p.setTag('x',namespace=NS_MUC).setTagData('password',CONF[1]) + p.getTag('x').addChild('history',{'maxchars':'0','maxstanzas':'0'}) + cl.send(p) + while 1: + cl.Process(1) diff --git a/src/xmpppy-0.5.0rc1/doc/examples/xsend.py b/src/xmpppy-0.5.0rc1/doc/examples/xsend.py new file mode 100755 index 00000000..59b202a9 --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/xsend.py @@ -0,0 +1,44 @@ +#!/usr/bin/python +# $Id: xsend.py,v 1.8 2006/10/06 12:30:42 normanr Exp $ +import sys,os,xmpp,time + +if len(sys.argv) < 2: + print "Syntax: xsend JID text" + sys.exit(0) + +tojid=sys.argv[1] +text=' '.join(sys.argv[2:]) + +jidparams={} +if os.access(os.environ['HOME']+'/.xsend',os.R_OK): + for ln in open(os.environ['HOME']+'/.xsend').readlines(): + if not ln[0] in ('#',';'): + key,val=ln.strip().split('=',1) + jidparams[key.lower()]=val +for mandatory in ['jid','password']: + if mandatory not in jidparams.keys(): + open(os.environ['HOME']+'/.xsend','w').write('#Uncomment fields before use and type in correct credentials.\n#JID=romeo@montague.net/resource (/resource is optional)\n#PASSWORD=juliet\n') + print 'Please point ~/.xsend config file to valid JID for sending messages.' + sys.exit(0) + +jid=xmpp.protocol.JID(jidparams['jid']) +cl=xmpp.Client(jid.getDomain(),debug=[]) + +con=cl.connect() +if not con: + print 'could not connect!' + sys.exit() +print 'connected with',con +auth=cl.auth(jid.getNode(),jidparams['password'],resource=jid.getResource()) +if not auth: + print 'could not authenticate!' + sys.exit() +print 'authenticated using',auth + +#cl.SendInitPresence(requestRoster=0) # you may need to uncomment this for old server +id=cl.send(xmpp.protocol.Message(tojid,text)) +print 'sent message with id',id + +time.sleep(1) # some older servers will not send the message if you disconnect immediately after sending + +#cl.disconnect() diff --git a/src/xmpppy-0.5.0rc1/doc/examples/xtalk.py b/src/xmpppy-0.5.0rc1/doc/examples/xtalk.py new file mode 100644 index 00000000..8832875f --- /dev/null +++ b/src/xmpppy-0.5.0rc1/doc/examples/xtalk.py @@ -0,0 +1,83 @@ +#!/usr/bin/python +# $Id: xtalk.py,v 1.4 2008/08/09 17:00:18 normanr Exp $ +import sys,os,xmpp,time,select + +class Bot: + + def __init__(self,jabber,remotejid): + self.jabber = jabber + self.remotejid = remotejid + + def register_handlers(self): + self.jabber.RegisterHandler('message',self.xmpp_message) + + def xmpp_message(self, con, event): + type = event.getType() + fromjid = event.getFrom().getStripped() + body = event.getBody() + if type in ['message', 'chat', None] and fromjid == self.remotejid and body: + sys.stdout.write(body + '\n') + + def stdio_message(self, message): + m = xmpp.protocol.Message(to=self.remotejid,body=message,typ='chat') + self.jabber.send(m) + + def xmpp_connect(self): + con=self.jabber.connect() + if not con: + sys.stderr.write('could not connect!\n') + return False + sys.stderr.write('connected with %s\n'%con) + auth=self.jabber.auth(jid.getNode(),jidparams['password'],resource=jid.getResource()) + if not auth: + sys.stderr.write('could not authenticate!\n') + return False + sys.stderr.write('authenticated using %s\n'%auth) + self.register_handlers() + return con + +if __name__ == '__main__': + + if len(sys.argv) < 2: + print "Syntax: xtalk JID" + sys.exit(0) + + tojid=sys.argv[1] + + jidparams={} + if os.access(os.environ['HOME']+'/.xtalk',os.R_OK): + for ln in open(os.environ['HOME']+'/.xtalk').readlines(): + if not ln[0] in ('#',';'): + key,val=ln.strip().split('=',1) + jidparams[key.lower()]=val + for mandatory in ['jid','password']: + if mandatory not in jidparams.keys(): + open(os.environ['HOME']+'/.xtalk','w').write('#Uncomment fields before use and type in correct credentials.\n#JID=romeo@montague.net/resource (/resource is optional)\n#PASSWORD=juliet\n') + print 'Please point ~/.xtalk config file to valid JID for sending messages.' + sys.exit(0) + + jid=xmpp.protocol.JID(jidparams['jid']) + cl=xmpp.Client(jid.getDomain())#,debug=[]) + + bot=Bot(cl,tojid) + + if not bot.xmpp_connect(): + sys.stderr.write("Could not connect to server, or password mismatch!\n") + sys.exit(1) + + #cl.SendInitPresence(requestRoster=0) # you may need to uncomment this for old server + + socketlist = {cl.Connection._sock:'xmpp',sys.stdin:'stdio'} + online = 1 + + while online: + (i , o, e) = select.select(socketlist.keys(),[],[],1) + for each in i: + if socketlist[each] == 'xmpp': + cl.Process(1) + elif socketlist[each] == 'stdio': + msg = sys.stdin.readline().rstrip('\r\n') + bot.stdio_message(msg) + else: + raise Exception("Unknown socket type: %s" % repr(socketlist[each])) + #cl.disconnect() |