Powering your website with realtime data

79
October 2011 Powering your website with realtime data Bert Van Hauwaert [email protected] - @tbotwit

description

We live in a very fast world. We want to know everything as soon as possible. We want realtime data! With XMPP you can power your website with realtime data. I will demonstrate a full setup with an Openfire XMPP server exchanging data with a PHP application. I will also explain the required JavaScript functions in order to send/receive messages through XMPP over BOSH.

Transcript of Powering your website with realtime data

Page 1: Powering your website with realtime data

October 2011

Powering your website with realtime data

Bert Van [email protected] - @tbotwit

Page 2: Powering your website with realtime data

Bert Van Hauwaert

• Live in Belgium

• Founder of be.coded

• Freelance web application developer & consultant

• ZCE 5.0

• Working on realtime auction sites

Page 3: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 4: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 5: Powering your website with realtime data

The old days

• <meta http-equiv=”refresh” content=”5” />

• <script >

• AJAX

Page 6: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 7: Powering your website with realtime data

XMPP: what

• Extensible Messaging and Presence Protocol

• Jabber

• XML

• Client - Server - Component

Page 8: Powering your website with realtime data

XMPP: stanzas

• <presence>

• <message>

• <iq>

Page 9: Powering your website with realtime data

XMPP: stanzas

• <presence>

• <message>

• <iq>

Page 10: Powering your website with realtime data

XMPP: stanzas

• <presence>

• <message>

• <iq>

Page 11: Powering your website with realtime data

XMPP: stanzas

• <presence>

• <message>

• <iq>

Page 12: Powering your website with realtime data

XMPP: addressing

• JID (Jabber Identifier)

• Three main parts

• [ node "@" ] domain [ "/" resource ]

Page 13: Powering your website with realtime data

XMPP: extensions

• XMPP Extension Protocol - XEP

• http://xmpp.org/xmpp-protocols/xmpp-extensions/

Page 14: Powering your website with realtime data

XMPP: advantages

• Open

• Decentralized

• Secure

• Extensible

Page 15: Powering your website with realtime data

XMPP: disadvantages

• Statefulness

• Overhead

Page 16: Powering your website with realtime data

XMPP: example<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status>Giving a talk @ ZendCon</status> </presence></stream:stream>

Page 17: Powering your website with realtime data

XMPP: example

<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status>Giving a talk @ ZendCon</status> </presence></stream:stream>

Page 18: Powering your website with realtime data

XMPP: example<stream:stream>

<iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status>Giving a talk @ ZendCon</status> </presence></stream:stream>

Page 19: Powering your website with realtime data

XMPP: example

<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq>

<presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status>Giving a talk @ ZendCon</status> </presence></stream:stream>

Page 20: Powering your website with realtime data

XMPP: example<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence />

<message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status>Giving a talk @ ZendCon</status> </presence></stream:stream>

Page 21: Powering your website with realtime data

XMPP: example<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message>

<presence> <show>dnd</show> <status> Giving a talk @ ZendCon </status> </presence></stream:stream>

Page 22: Powering your website with realtime data

XMPP: example<stream:stream> <iq type="get" id="roster1"> <query xmlns:"jabber:iq:roster" /> </iq> <presence /> <message to="[email protected]" from="[email protected]/speakerroom" type="chat"> <body> I hope you will enjoy this talk </body> </message> <presence> <show>dnd</show> <status> Giving a talk @ ZendCon </status> </presence>

</stream:stream>

Page 23: Powering your website with realtime data

XMPP: XEP-0060 (1)

• PubSub (Publish / Subscribe)

• Bandwidth / resources

Page 24: Powering your website with realtime data

XMPP: XEP-0060 (2)

<iqfrom="[email protected]/car" id="ams9nz78"to="pubsub.holiday.com"type="set"><pubsub xmlns="http://jabber.org/protocol/pubsub"><subscribe node="are-we-there-yet" jid="[email protected]"/>

</pubsub></iq>

Page 25: Powering your website with realtime data

XMPP: XEP-0060 (3)

<iqfrom="[email protected]/car" id="wmn78e45a" to="pubsub.holiday.com"type="set"><pubsub xmlns="http://jabber.org/protocol/pubsub"><publish node="are-we-there-yet"><item><there xmlns="http://holiday.com/there-yet" status="true"/>

</item></publish>

</pubsub></iq>

Page 26: Powering your website with realtime data

XMPP: XEP-0060 (4)

<message from="pubsub.holiday.com" to="[email protected]"><event xmlns="http://jabber.org/protocol/pubsub#event"><items node="are-we-there-yet"><item id="ax78ui789q"><there xmlns="http://holiday.com/there-yet" status="true"/>

</item></items>

</event></message>

Page 27: Powering your website with realtime data

XMPP: XEP-0045 (1)

• MUC / Multi-User Chat

• “Multiplier”

Page 28: Powering your website with realtime data

XMPP: XEP-0045 (2)

<presencefrom="[email protected]/resource" to="[email protected]/nickname"><x xmlns="http://jabber.org/protocol/muc"/>

</presence>

Page 29: Powering your website with realtime data

XMPP: XEP-0045 (3)

<message to="[email protected]"from="[email protected]/resource" type="groupchat "><body>Lorem Ipsum</body>

</message>

<message to="[email protected]/resource"from="[email protected]/nickname" type="groupchat "><body>Lorem Ipsum</body></message>

Page 30: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 31: Powering your website with realtime data

Install server: starting point

• Debian

• web server

• SQL database

• SSH server

Page 32: Powering your website with realtime data

Install server: apt sources

• apt-get install vim

• vim /etc/apt/sources.list

• deb http://ftp.belnet.be/debian/ squeeze main non-freedeb-src http://ftp.belnet.be/debian/ squeeze maindeb http://security.debian.org/ squeeze/updates main non-freedeb-src http://security.debian.org/ squeeze/updates maindeb http://packages.dotdeb.org stable alldeb-src http://packages.dotdeb.org stable all

Page 33: Powering your website with realtime data

Install server: prerequisites (1)

• wget http://www.dotdeb.org/dotdeb.gpg

• cat dotdeb.gpg | apt-key add -

• apt-get update

• apt-get install sun-java6-jre sun-java6-fonts ident2

Page 34: Powering your website with realtime data

Install server: prerequisites (2)

• apt-get install mysql-server mysql-client

• apt-get install php5 php5-cli php5-common php5-dev php5-mysql php5-curl php-pear

• Database & user

Page 36: Powering your website with realtime data

Install server: Openfire (2)

• http://[server-ip]:9090/

Page 37: Powering your website with realtime data
Page 38: Powering your website with realtime data
Page 39: Powering your website with realtime data
Page 40: Powering your website with realtime data
Page 41: Powering your website with realtime data
Page 42: Powering your website with realtime data
Page 43: Powering your website with realtime data
Page 44: Powering your website with realtime data

Install server: Openfire (3)

• Plugins

• User Service

• Monitoring Service

Page 45: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 46: Powering your website with realtime data

Configure apache: why(1)

Client - polling

Server

Client - long polling

new data

no d

ata

no d

ata

no d

ata

data

data

Page 47: Powering your website with realtime data

Configure apache: why(2)

• BOSH (Bidirectional streams Over Synchronous HTTP)

Page 48: Powering your website with realtime data

Configure apache: proxy (1)

• cd /etc/apache2/mods-enabled/

• ln -s ../mods-available/proxy.load

• ln -s ../mods-available/proxy_http.load

• ln -s ../mods-available/rewrite.load

Page 49: Powering your website with realtime data

Configure apache: proxy (2)

<VirtualHost *:80> Options FollowSymLinks ServerAdmin [email protected] ServerName xmpp.dev.becoded.be ServerAlias static.xmpp.dev.becoded.be # Indexes + Directory Root. DirectoryIndex index.php DocumentRoot /var/www/vhost/xmpp.dev.becoded.be/htdocs/public/ php_admin_value open_basedir ".:/var/www/vhost/xmpp.dev.becoded.be/htdocs:/var/www/library/Zend-latest/library:../:/usr/share/php:/tmp" php_value include_path ".:/var/www/vhost/xmpp.dev.becoded.be/htdocs:/var/www/library/Zend-latest/library:/usr/share/php" php_admin_value upload_tmp_dir "/tmp" SetEnv APPLICATION_ENV development

# Logfiles ErrorLog /var/www/vhost/xmpp.dev.becoded.be/logs/error.log CustomLog /var/www/vhost/xmpp.dev.becoded.be/logs/access.log combined

# XMPP proxy ruleProxyRequests OffProxyPass /bind http://127.0.0.1:7070/http-bind/ProxyPassReverse /bind http://127.0.0.1:7070/http-bind/</VirtualHost>

Page 50: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 51: Powering your website with realtime data

Libraries

• ZF - http://framework.zend.com

• jQuery - http://jquery.com/

• jQuery UI - http://jqueryui.com/

• XMPPHP - http://code.google.com/p/xmpphp

• Jaxl - http://jaxl.net

• Strophe.js - http://strophe.im

Page 52: Powering your website with realtime data

Libraries: XMPPHP

$connection = new XMPPHP_XMPP( $host, $port, $identifier->node, $identifier->password, $identifier->resource, $domain, $printlog, $loglevel);$connection->connect();$connection->processUntil('session_start');$connection->message('support@demo', 'Hello world');$connection->disconnect();

Page 53: Powering your website with realtime data

Libraries: Jaxl$connection = new JAXL(array( 'user' => $identifier->node, 'pass' => $identifier->password,

'host' => $host,'domain' => $domain,

'port' => $port, 'authType' => 'PLAIN', 'logLevel' => $loglevel ));$connection->addPlugin('jaxl_post_auth', '_postAuthHook');$connection->startCore("stream");

public function _postAuthHook ($payload, $jaxl) {$jaxl->sendMessage('support@demo', 'Hello world');$jaxl->shutdown();

}

Page 54: Powering your website with realtime data

Libraries: Strophe.jsvar connection = new Strophe.Connection('/bind');connection.connect( jid, password, function (status) { if (status == Strophe.Status.CONNECTED) { var msg = $msg({ to : 'support@demo', type : "chat" }).c('body').t('Hello world'); connection.send(msg); setTimeout(function () { connection.disconnect(); }, 500); } });

Page 55: Powering your website with realtime data

Overview

• The old days

• XMPP

• Install server

• Configure apache

• Libraries

• Examples

Page 56: Powering your website with realtime data

Examples: setup

Page 57: Powering your website with realtime data
Page 58: Powering your website with realtime data

Examples: messages

• Browser

• Log

• Adium

Page 59: Powering your website with realtime data
Page 60: Powering your website with realtime data
Page 61: Powering your website with realtime data

Example: IQ ping pong (1)

this.statusHandler = function (status) { var me = this; if (status == Strophe.Status.CONNECTED) { me.connection.addHandler( function(msg) { //(Function) handler return me.handlePong(msg); },

null, //(String) ns 'iq', //(String) name null, //(String) type 'pingPong'); //(String) id me.sendPing(Strophe.getDomainFromJid(me.connection.jid)); } };

Page 62: Powering your website with realtime data

Example: IQ ping pong (2)

this.sendPing = function (to){ var me = this; var iq = $iq({ to: to, type : 'get', id : 'pingPong' }).c('ping',

{xmlns: 'urn:xmpp:ping'}); me.connection.send(iq);};

<iq to='demo' type='get' id='pingPong' xmlns='jabber:client'> <ping

xmlns='urn:xmpp:ping'/></iq>

Page 63: Powering your website with realtime data

Example: IQ ping pong (3)

this.handlePong = function (msg){ var me = this; var objMsg = $(msg); var from = objMsg.attr('from'); me.log('Receiving ' + objMsg.attr('type') + ' from "' + objMsg.attr('from') + '" with id "' + objMsg.attr('id') + '"'); me.connection.disconnect();};

<iq xmlns="jabber:client" type="result" id="pingPong" from="demo" to="demo1@demo/eeffca60"/>

Page 64: Powering your website with realtime data
Page 65: Powering your website with realtime data

Example: support chat (1)

this.bindSendMessage = function (){ var me = this; var chatMsg = $('#message'); $('#sendMessage').bind('click', function() { me.sendChatMessage(chatMsg.val()); me.resetTextarea(chatMsg); }); chatMsg.keyup(function(event) { if (event.keyCode == 13 && event.shiftKey) { me.sendChatMessage(chatMsg.val()); me.resetTextarea(chatMsg); } });};

Page 66: Powering your website with realtime data

Example: support chat (2)

this.statusHandler = function (status){ var me = this; me.logStatus(status); if (status == Strophe.Status.CONNECTED) { me.connection.addHandler( function(msg) { //(Function) handler. return me.handleChatMessage(msg); }, null, //(String) ns 'message', //(String) name 'chat'); //(String) type }};

Page 67: Powering your website with realtime data

Example: support chat (3)

this.handleChatMessage = function (msg){ var me = this; var objMsg = $(msg); var from = objMsg.attr('from'); var nick = Strophe.getNodeFromJid(from); var body = objMsg.children('body').text(); me.addMessageToChat(nick, body); return true;};

Page 68: Powering your website with realtime data

Example: support chat (4)

this.addMessageToChat = function (nick, body){ var me = this; var container = $('#chat'); var atBottom =

container.scrollTop() >= container[0].scrollHeight - container.height();

container.append('<dt>'+ nick +'</dt><dd>'+

me.nl2br(body, true) +'</dd>'); if (atBottom) { container.scrollTop(container[0].scrollHeight); }};

Page 69: Powering your website with realtime data
Page 70: Powering your website with realtime data

Example: statistics

this.handleHighChartData = function (msg){ var me = this; var objMsg = $(msg);

var body = objMsg.children('body').text(); me.chart.series[0].setData(jQuery.parseJSON(body)); return true;};

Page 71: Powering your website with realtime data
Page 72: Powering your website with realtime data
Page 73: Powering your website with realtime data

Example: prebind BOSH (1)

• SID - RID

• Security

• User friendly

• Performance

• Persisting

Page 74: Powering your website with realtime data

Example: prebind BOSH(2)

this.initConnection = function (){ var me = this;

me.connection = new Strophe.Connection(me.httpBindUrl); me.connection.attach( me.options.service.jid, me.options.service.sid, me.options.service.rid, function (status) { me.statusHandler(status); });};

Page 75: Powering your website with realtime data
Page 76: Powering your website with realtime data
Page 77: Powering your website with realtime data

Books

Page 78: Powering your website with realtime data

Thank you

[email protected]

• Code: https://github.com/becoded/talk-xmpp-demo

• Slides: Slideshare

• Rate / comments: http://joind.in/3778

Page 79: Powering your website with realtime data

Questions

? ? ? ?