aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--CHANGES1
-rw-r--r--plugins/mod_csi_simple.lua100
-rw-r--r--prosody.cfg.lua.dist8
-rw-r--r--spec/scansion/pep_publish_subscribe.scs210
4 files changed, 317 insertions, 2 deletions
diff --git a/CHANGES b/CHANGES
index d43d316f..a5c185cc 100644
--- a/CHANGES
+++ b/CHANGES
@@ -22,6 +22,7 @@ New features
- mod\_muc\_mam (XEP-0313 in groupchats)
- mod\_vcard\_legacy (XEP-0398)
- mod\_vcard4 (XEP-0292)
+- mod\_csi, mod\_csi\_simple (XEP-0352)
- New experimental network backend "epoll"
0.10.0
diff --git a/plugins/mod_csi_simple.lua b/plugins/mod_csi_simple.lua
new file mode 100644
index 00000000..1535edae
--- /dev/null
+++ b/plugins/mod_csi_simple.lua
@@ -0,0 +1,100 @@
+-- Copyright (C) 2016-2018 Kim Alvefur
+--
+-- This project is MIT/X11 licensed. Please see the
+-- COPYING file in the source package for more information.
+--
+
+module:depends"csi"
+
+local jid = require "util.jid";
+local st = require "util.stanza";
+local dt = require "util.datetime";
+local new_queue = require "util.queue".new;
+
+local function new_pump(output, ...)
+ -- luacheck: ignore 212/self
+ local q = new_queue(...);
+ local flush = true;
+ function q:pause()
+ flush = false;
+ end
+ function q:resume()
+ flush = true;
+ return q:flush();
+ end
+ local push = q.push;
+ function q:push(item)
+ local ok = push(self, item);
+ if not ok then
+ q:flush();
+ output(item, self);
+ elseif flush then
+ return q:flush();
+ end
+ return true;
+ end
+ function q:flush()
+ local item = self:pop();
+ while item do
+ output(item, self);
+ item = self:pop();
+ end
+ return true;
+ end
+ return q;
+end
+
+local queue_size = module:get_option_number("csi_queue_size", 256);
+
+module:hook("csi-is-stanza-important", function (event)
+ local stanza = event.stanza;
+ local st_name = stanza.name;
+ if not st_name then return false; end
+ local st_type = stanza.attr.type;
+ if st_name == "presence" then
+ if st_type == nil or st_type == "unavailable" then
+ return false;
+ end
+ return true;
+ elseif st_name == "message" then
+ if st_type == "headline" then
+ return false;
+ end
+ local body = stanza:get_child_text("body");
+ return body;
+ end
+ return true;
+end, -1);
+
+module:hook("csi-client-inactive", function (event)
+ local session = event.origin;
+ if session.pump then
+ session.pump:pause();
+ else
+ local bare_jid = jid.join(session.username, session.host);
+ local send = session.send;
+ session._orig_send = send;
+ local pump = new_pump(session.send, queue_size);
+ pump:pause();
+ session.pump = pump;
+ function session.send(stanza)
+ if module:fire_event("csi-stanza-is-important", { stanza = stanza, session = session }) then
+ pump:flush();
+ send(stanza);
+ else
+ stanza = st.clone(stanza);
+ stanza:add_direct_child(st.stanza("delay", {xmlns = "urn:xmpp:delay", from = bare_jid, stamp = dt.datetime()}));
+ pump:push(stanza);
+ end
+ return true;
+ end
+ end
+end);
+
+module:hook("csi-client-active", function (event)
+ local session = event.origin;
+ if session.pump then
+ session.pump:resume();
+ end
+end);
+
diff --git a/prosody.cfg.lua.dist b/prosody.cfg.lua.dist
index a0fc6c9e..b6ea2ecb 100644
--- a/prosody.cfg.lua.dist
+++ b/prosody.cfg.lua.dist
@@ -46,10 +46,11 @@ modules_enabled = {
-- Not essential, but recommended
"carbons"; -- Keep multiple clients in sync
- "pep"; -- Enables users to publish their mood, activity, playing music and more
+ "pep"; -- Enables users to publish their avatar, mood, activity, playing music and more
"private"; -- Private XML storage (for room bookmarks, etc.)
"blocklist"; -- Allow users to block communications with other users
- "vcard"; -- Allow users to set vCards
+ "vcard4"; -- User profiles (stored in PEP)
+ "vcard_legacy"; -- Conversion between legacy vCard and PEP Avatar, vcard
-- Nice to have
"version"; -- Replies to server version requests
@@ -58,6 +59,7 @@ modules_enabled = {
"ping"; -- Replies to XMPP pings with pongs
"register"; -- Allow users to register on this server using a client and change passwords
--"mam"; -- Store messages in an archive and allow users to access it
+ --"csi_simple"; -- Simple Mobile optimizations
-- Admin interfaces
"admin_adhoc"; -- Allows administration via an XMPP client that supports ad-hoc commands
@@ -197,6 +199,8 @@ VirtualHost "localhost"
---Set up a MUC (multi-user chat) room server on conference.example.com:
--Component "conference.example.com" "muc"
+--- Store MUC messages in an archive and allow users to access it
+--modules_enabled = { "muc_mam" }
---Set up an external component (default component port is 5347)
--
diff --git a/spec/scansion/pep_publish_subscribe.scs b/spec/scansion/pep_publish_subscribe.scs
new file mode 100644
index 00000000..e8080134
--- /dev/null
+++ b/spec/scansion/pep_publish_subscribe.scs
@@ -0,0 +1,210 @@
+# PEP publish, subscribe and publish-options
+
+[Client] Romeo
+ jid: pep-test-wjebo4kg@localhost
+ password: password
+
+[Client] Juliet
+ jid: pep-test-tqvqu_pv@localhost
+ password: password
+
+-----
+
+Romeo connects
+
+Romeo sends:
+ <presence>
+ <c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/>
+ </presence>
+
+Romeo receives:
+ <iq type='get' id='disco' from="${Romeo's JID}">
+ <query node='http://code.matthewwild.co.uk/verse/#PDH7CGVPRERS2WUqBD18PHGEzaY=' xmlns='http://jabber.org/protocol/disco#info'/>
+ </iq>
+
+Romeo receives:
+ <presence from="${Romeo's full JID}">
+ <c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/>
+ </presence>
+
+Romeo sends:
+ <iq type='get' id='6'>
+ <query ver='' xmlns='jabber:iq:roster'/>
+ </iq>
+
+Romeo receives:
+ <iq type='result' id='6'>
+ <query ver='1' xmlns='jabber:iq:roster'/>
+ </iq>
+
+Juliet connects
+
+Juliet sends:
+ <presence>
+ <c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/>
+ </presence>
+
+Juliet receives:
+ <iq type='get' id='disco' from="${Juliet's JID}">
+ <query node='http://code.matthewwild.co.uk/verse/#PDH7CGVPRERS2WUqBD18PHGEzaY=' xmlns='http://jabber.org/protocol/disco#info'/>
+ </iq>
+
+Juliet receives:
+ <presence from="${Juliet's full JID}">
+ <c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/>
+ </presence>
+
+Juliet sends:
+ <iq type='get' id='6'>
+ <query ver='' xmlns='jabber:iq:roster'/>
+ </iq>
+
+Juliet receives:
+ <iq type='result' id='6'>
+ <query ver='1' xmlns='jabber:iq:roster'/>
+ </iq>
+
+Romeo sends:
+ <iq type='result' id='disco' to='pep-test-wjebo4kg@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#PDH7CGVPRERS2WUqBD18PHGEzaY='><identity type='pc' name='Verse' category='client'/><feature var='http://jabber.org/protocol/disco#info'/><feature var='http://jabber.org/protocol/disco#items'/><feature var='http://jabber.org/protocol/caps'/></query></iq>
+
+Romeo sends:
+ <presence type='subscribe' to="${Juliet's JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='set' id='{scansion:any}'><query ver='1' xmlns='jabber:iq:roster'><item ask='subscribe' jid='pep-test-tqvqu_pv@localhost' subscription='none'/></query></iq>
+
+Romeo receives:
+ <presence type='unavailable' to='pep-test-wjebo4kg@localhost' from='pep-test-tqvqu_pv@localhost'/>
+
+Juliet receives:
+ <presence type='subscribe' from='pep-test-wjebo4kg@localhost' to='pep-test-tqvqu_pv@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Juliet sends:
+ <iq type='result' id='disco' to='pep-test-tqvqu_pv@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#PDH7CGVPRERS2WUqBD18PHGEzaY='><identity type='pc' name='Verse' category='client'/><feature var='http://jabber.org/protocol/disco#info'/><feature var='http://jabber.org/protocol/disco#items'/><feature var='http://jabber.org/protocol/caps'/></query></iq>
+
+Juliet sends:
+ <presence type='subscribe' to="${Romeo's JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Juliet receives:
+ <iq type='set' id='{scansion:any}'><query ver='2' xmlns='jabber:iq:roster'><item ask='subscribe' jid='pep-test-wjebo4kg@localhost' subscription='none'/></query></iq>
+
+Juliet receives:
+ <presence type='unavailable' to='pep-test-tqvqu_pv@localhost' from='pep-test-wjebo4kg@localhost'/>
+
+Romeo receives:
+ <presence type='subscribe' from='pep-test-tqvqu_pv@localhost' to='pep-test-wjebo4kg@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo sends:
+ <iq type='result' id='fixme'/>
+
+Romeo sends:
+ <presence type='subscribed' to='pep-test-tqvqu_pv@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='set' id='{scansion:any}'><query ver='3' xmlns='jabber:iq:roster'><item ask='subscribe' jid='pep-test-tqvqu_pv@localhost' subscription='from'/></query></iq>
+
+Juliet receives:
+ <presence type='subscribed' from='pep-test-wjebo4kg@localhost' to='pep-test-tqvqu_pv@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Juliet receives:
+ <iq type='set' id='{scansion:any}'><query ver='3' xmlns='jabber:iq:roster'><item jid='pep-test-wjebo4kg@localhost' subscription='to'/></query></iq>
+
+Juliet receives:
+ <presence to='pep-test-tqvqu_pv@localhost' from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/><delay xmlns='urn:xmpp:delay' stamp='{scansion:any}' from='localhost'/></presence>
+
+Juliet sends:
+ <presence type='subscribed' to='pep-test-wjebo4kg@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Juliet receives:
+ <iq type='set' id='{scansion:any}'><query ver='4' xmlns='jabber:iq:roster'><item jid='pep-test-wjebo4kg@localhost' subscription='both'/></query></iq>
+
+Juliet receives:
+ <presence to='pep-test-tqvqu_pv@localhost' from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/><delay xmlns='urn:xmpp:delay' stamp='{scansion:any}' from='localhost'/></presence>
+
+Romeo receives:
+ <presence type='subscribed' from='pep-test-tqvqu_pv@localhost' to='pep-test-wjebo4kg@localhost'><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='set' id='{scansion:any}'><query ver='4' xmlns='jabber:iq:roster'><item jid='pep-test-tqvqu_pv@localhost' subscription='both'/></query></iq>
+
+Romeo receives:
+ <presence to='pep-test-wjebo4kg@localhost' from="${Juliet's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='PDH7CGVPRERS2WUqBD18PHGEzaY=' node='http://code.matthewwild.co.uk/verse/'/><delay xmlns='urn:xmpp:delay' stamp='{scansion:any}' from='localhost'/></presence>
+
+Juliet sends:
+ <iq type='result' id='fixme'/>
+
+Romeo sends:
+ <iq type='result' id='fixme'/>
+
+Romeo sends:
+ <iq type='result' id='fixme'/>
+
+Romeo sends:
+ <presence><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='m/sIsyfzKk8X1okZMtStR43nQQg=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='get' id='disco' from='pep-test-wjebo4kg@localhost'><query node='http://code.matthewwild.co.uk/verse/#m/sIsyfzKk8X1okZMtStR43nQQg=' xmlns='http://jabber.org/protocol/disco#info'/></iq>
+
+Romeo receives:
+ <presence from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='m/sIsyfzKk8X1okZMtStR43nQQg=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='get' id='disco' from='pep-test-tqvqu_pv@localhost'><query node='http://code.matthewwild.co.uk/verse/#m/sIsyfzKk8X1okZMtStR43nQQg=' xmlns='http://jabber.org/protocol/disco#info'/></iq>
+
+Juliet receives:
+ <presence from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='m/sIsyfzKk8X1okZMtStR43nQQg=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo sends:
+ <presence><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='IfQwbaaDB4LEP5tkGArEaB/3Y+s=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='get' id='disco' from='pep-test-wjebo4kg@localhost'><query node='http://code.matthewwild.co.uk/verse/#IfQwbaaDB4LEP5tkGArEaB/3Y+s=' xmlns='http://jabber.org/protocol/disco#info'/></iq>
+
+Romeo receives:
+ <presence from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='IfQwbaaDB4LEP5tkGArEaB/3Y+s=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Romeo receives:
+ <iq type='get' id='disco' from='pep-test-tqvqu_pv@localhost'><query node='http://code.matthewwild.co.uk/verse/#IfQwbaaDB4LEP5tkGArEaB/3Y+s=' xmlns='http://jabber.org/protocol/disco#info'/></iq>
+
+Romeo sends:
+ <iq type='result' id='disco' to='pep-test-wjebo4kg@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#m/sIsyfzKk8X1okZMtStR43nQQg='/></iq>
+
+Romeo sends:
+ <iq type='result' id='disco' to='pep-test-tqvqu_pv@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#m/sIsyfzKk8X1okZMtStR43nQQg='/></iq>
+
+Romeo sends:
+ <iq type='result' id='disco' to='pep-test-wjebo4kg@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#IfQwbaaDB4LEP5tkGArEaB/3Y+s='><identity type='pc' name='Verse' category='client'/><feature var='http://jabber.org/protocol/tune+notify'/><feature var='http://jabber.org/protocol/disco#info'/><feature var='http://jabber.org/protocol/disco#items'/><feature var='http://jabber.org/protocol/caps'/><feature var='http://jabber.org/protocol/mood+notify'/></query></iq>
+
+Juliet receives:
+ <presence from="${Romeo's full JID}"><c xmlns='http://jabber.org/protocol/caps' hash='sha-1' ver='IfQwbaaDB4LEP5tkGArEaB/3Y+s=' node='http://code.matthewwild.co.uk/verse/'/></presence>
+
+Juliet sends:
+ <iq type='result' id='fixme'/>
+
+Juliet sends:
+ <iq type='set' id='7'><pubsub xmlns='http://jabber.org/protocol/pubsub'><publish node='http://jabber.org/protocol/tune'><item id='current'><tune xmlns='http://jabber.org/protocol/tune'><title>Beautiful Cedars</title><artist>The Spinners</artist><source>Not Quite Folk</source><track>4</track></tune></item></publish></pubsub></iq>
+
+Juliet receives:
+ <iq type='result' id='7' ><pubsub xmlns='http://jabber.org/protocol/pubsub'><publish node='http://jabber.org/protocol/tune'><item id='current'/></publish></pubsub></iq>
+
+Juliet sends:
+ <iq type='set' id='8'><pubsub xmlns='http://jabber.org/protocol/pubsub'><publish node='http://jabber.org/protocol/mood'><item><mood xmlns='http://jabber.org/protocol/mood'><happy/></mood></item></publish><publish-options><x type='submit' xmlns='jabber:x:data'><field type='hidden' var='FORM_TYPE'><value>http://jabber.org/protocol/pubsub#publish-options</value></field><field var='pubsub#persist_items'><value>true</value></field><field var='pubsub#access_model'><value>whitelist</value></field></x></publish-options></pubsub></iq>
+
+Juliet receives:
+ <iq type='result' id='8'><pubsub xmlns='http://jabber.org/protocol/pubsub'><publish node='http://jabber.org/protocol/mood'><item id='{scansion:any}'/></publish></pubsub></iq>
+
+Juliet sends:
+ <iq type='result' id='{scansion:any}'/>
+
+Romeo receives:
+ <message type='headline' from='pep-test-tqvqu_pv@localhost'><event xmlns='http://jabber.org/protocol/pubsub#event'><items node='http://jabber.org/protocol/tune'><item id='current'><tune xmlns='http://jabber.org/protocol/tune'><title>Beautiful Cedars</title><artist>The Spinners</artist><source>Not Quite Folk</source><track>4</track></tune></item></items></event></message>
+
+Romeo sends:
+ <iq type='result' id='disco' to='pep-test-tqvqu_pv@localhost'><query xmlns='http://jabber.org/protocol/disco#info' node='http://code.matthewwild.co.uk/verse/#IfQwbaaDB4LEP5tkGArEaB/3Y+s='><identity type='pc' name='Verse' category='client'/><feature var='http://jabber.org/protocol/tune+notify'/><feature var='http://jabber.org/protocol/disco#info'/><feature var='http://jabber.org/protocol/disco#items'/><feature var='http://jabber.org/protocol/caps'/><feature var='http://jabber.org/protocol/mood+notify'/></query></iq>
+
+Romeo receives:
+ <message type='headline' from='pep-test-tqvqu_pv@localhost'><event xmlns='http://jabber.org/protocol/pubsub#event'><items node='http://jabber.org/protocol/tune'><item id='current'><tune xmlns='http://jabber.org/protocol/tune'><title>Beautiful Cedars</title><artist>The Spinners</artist><source>Not Quite Folk</source><track>4</track></tune></item></items></event></message>
+
+Juliet disconnects
+
+Romeo disconnects