Skip to content

Commit

Permalink
Add support for XEP-0198 Stream Management
Browse files Browse the repository at this point in the history
- New plugin `converse-smacks`
- New config option `enable_smacks`
- Rename session cache id from `converse.bosh-session` to `converse.session`

Updates #316
  • Loading branch information
jcbrand committed May 31, 2019
1 parent 918f287 commit 0dffe29
Show file tree
Hide file tree
Showing 8 changed files with 279 additions and 34 deletions.
11 changes: 6 additions & 5 deletions CHANGES.md
Expand Up @@ -15,15 +15,15 @@
- Message deduplication bugfixes and improvements
- Continuously retry (in 2s intervals) to fetch login credentials (via [credentials_url](https://conversejs.org/docs/html/configuration.html#credentials-url)) in case of failure
- Replace `moment` with [DayJS](https://github.com/iamkun/dayjs).
- New API method [\_converse.api.disco.features.get](https://conversejs.org/docs/html/api/-_converse.api.disco.features.html#.get)
- New config setting [muc_show_join_leave_status](https://conversejs.org/docs/html/configuration.html#muc-show-join-leave-status)
- New config option [enable_smacks](https://conversejs.org/docs/html/configuration.html#enable-smacks).
- New config option [muc_show_join_leave_status](https://conversejs.org/docs/html/configuration.html#muc-show-join-leave-status)
- New config option [singleton](https://conversejs.org/docs/html/configuration.html#singleton).
By setting this option to `false` and `view_mode` to `'embedded'`, it's now possible to
"embed" the full app and not just a single chat. To embed just a single chat, it's now
necessary to explicitly set `singleton` to `true`.
- New event: `chatBoxBlurred`.
- New event: [chatBoxBlurred](https://conversejs.org/docs/html/api/-_converse.html#event:chatBoxBlurred)
- New event: [chatReconnected](https://conversejs.org/docs/html/api/-_converse.html#event:chatReconnected)
- #316: Add support for XEP-0198 Stream Management
- #1296: `embedded` view mode shows `chatbox-navback` arrow in header
- #1465: When highlighting a roster contact, they're incorrectly shown as online
- #1532: Converse reloads on enter pressed in the filter box
Expand All @@ -34,12 +34,12 @@
- #1576: Converse gets stuck with spinner when logging out with `auto_login` set to `true`
- #1586: Not possible to kick someone with a space in their nickname

- **Breaking changes**:
### Breaking changes

- Rename `muc_disable_moderator_commands` to [muc_disable_slash_commands](https://conversejs.org/docs/html/configuration.html#muc-disable-slash-commands).
- `_converse.api.archive.query` now returns a Promise instead of accepting a callback functions.
- `_converse.api.disco.supports` now returns a Promise which resolves to a Boolean instead of an Array.


### API changes

- `_converse.chats.open` and `_converse.rooms.open` now take a `force`
Expand All @@ -49,6 +49,7 @@
- `_converse.api.emit` has been removed in favor of [\_converse.api.trigger](https://conversejs.org/docs/html/api/-_converse.api.html#.trigger)
- `_converse.updateSettings` has been removed in favor of [\_converse.api.settings.update](https://conversejs.org/docs/html/api/-_converse.api.settings.html#.update)
- `_converse.api.roster.get` now returns a promise.
- New API method [\_converse.api.disco.features.get](https://conversejs.org/docs/html/api/-_converse.api.disco.features.html#.get)

## 4.2.0 (2019-04-04)

Expand Down
19 changes: 19 additions & 0 deletions docs/source/configuration.rst
Expand Up @@ -635,6 +635,15 @@ The app servers are specified with the `push_app_servers`_ option.
Registering a push app server against a MUC domain is not (yet) standardized
and this feature should be considered experimental.

enable_smacks
-------------

* Default: ``false``

Determines whether `XEP-0198 Stream Management <https://xmpp.org/extensions/xep-0198.html>`_
support is turned on or not.


expose_rid_and_sid
------------------

Expand Down Expand Up @@ -1398,6 +1407,16 @@ want to embed a chat into the page.
Alternatively you could use it with `view_mode`_ set to ``overlayed`` to create
a single helpdesk-type chat.


smacks_max_unacked_stanzas
--------------------------

* Default: ``5``

This setting relates to `XEP-0198 <https://xmpp.org/extensions/xep-0198.html>`_
and determines the number of stanzas to be sent before Converse will ask the
server for acknowledgement of those stanzas.

sounds_path
-----------

Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion src/headless/converse-core.js
Expand Up @@ -102,6 +102,7 @@ _converse.core_plugins = [
'converse-pubsub',
'converse-roster',
'converse-rsm',
'converse-smacks',
'converse-vcard'
];

Expand Down Expand Up @@ -439,7 +440,7 @@ _converse.initConnection = function () {


async function initSession () {
const id = 'converse.bosh-session';
const id = 'converse.session';
_converse.session = new Backbone.Model({id});
_converse.session.browserStorage = new BrowserStorage.session(id);
try {
Expand Down
63 changes: 38 additions & 25 deletions src/headless/converse-disco.js
Expand Up @@ -22,6 +22,7 @@ converse.plugins.add('converse-disco', {

// Promises exposed by this plugin
_converse.api.promises.add('discoInitialized');
_converse.api.promises.add('streamFeaturesAdded');


/**
Expand Down Expand Up @@ -260,32 +261,33 @@ converse.plugins.add('converse-disco', {
}

function initStreamFeatures () {
_converse.stream_features = new Backbone.Collection();
_converse.stream_features.browserStorage = new BrowserStorage.session(
`converse.stream-features-${_converse.bare_jid}`
);
_converse.stream_features.fetch({
success (collection) {
if (collection.length === 0 && _converse.connection.features) {
_.forEach(
_converse.connection.features.childNodes,
(feature) => {
_converse.stream_features.create({
'name': feature.nodeName,
'xmlns': feature.getAttribute('xmlns')
const bare_jid = Strophe.getBareJidFromJid(_converse.jid);
const id = `converse.stream-features-${bare_jid}`;
if (!_converse.stream_features || _converse.stream_features.browserStorage.id !== id) {
_converse.stream_features = new Backbone.Collection();
_converse.stream_features.browserStorage = new BrowserStorage.session(id);
_converse.stream_features.fetch({
success (collection) {
if (collection.length === 0 && _converse.connection.features) {
Array.from(_converse.connection.features.childNodes)
.forEach(feature => {
_converse.stream_features.create({
'name': feature.nodeName,
'xmlns': feature.getAttribute('xmlns')
});
});
});
}
/**
* Triggered as soon as Converse has processed the stream features as advertised by
* the server. If you want to check whether a stream feature is supported before
* proceeding, then you'll first want to wait for this event.
* @event _converse#streamFeaturesAdded
* @example _converse.api.listen.on('streamFeaturesAdded', () => { ... });
*/
_converse.api.trigger('streamFeaturesAdded');
}
}
});
/**
* Triggered as soon as Converse has processed the stream features as advertised by
* the server. If you want to check whether a stream feature is supported before
* proceeding, then you'll first want to wait for this event.
* @event _converse#streamFeaturesAdded
* @example _converse.api.listen.on('streamFeaturesAdded', () => { ... });
*/
_converse.api.trigger('streamFeaturesAdded');
});
}
}

async function initializeDisco () {
Expand Down Expand Up @@ -313,7 +315,13 @@ converse.plugins.add('converse-disco', {
_converse.api.trigger('discoInitialized');
}

// beforeResourceBinding may or may not fire, depending on whether
// 'explicitResourceBinding` was set to true or false when
// Strophe.Connection was instantiated, so we also listen for
// setUserJID
_converse.api.listen.on('beforeResourceBinding', initStreamFeatures);
_converse.api.listen.on('setUserJID', initStreamFeatures);

_converse.api.listen.on('reconnected', initializeDisco);
_converse.api.listen.on('connected', initializeDisco);

Expand All @@ -326,6 +334,10 @@ converse.plugins.add('converse-disco', {
_converse.disco_entities.reset();
_converse.disco_entities.browserStorage._clear();
}
if (_converse.stream_features) {
_converse.stream_features.reset();
_converse.stream_features.browserStorage._clear();
}
});

const plugin = this;
Expand Down Expand Up @@ -386,7 +398,8 @@ converse.plugins.add('converse-disco', {
* @param {String} xmlns The XML namespace
* @example _converse.api.disco.stream.getFeature('ver', 'urn:xmpp:features:rosterver')
*/
'getFeature': function (name, xmlns) {
'getFeature': async function (name, xmlns) {
await _converse.api.waitUntil('streamFeaturesAdded');
if (_.isNil(name) || _.isNil(xmlns)) {
throw new Error("name and xmlns need to be provided when calling disco.stream.getFeature");
}
Expand Down

0 comments on commit 0dffe29

Please sign in to comment.