Socket
Socket
Sign inDemoInstall

@roomservice/browser

Package Overview
Dependencies
Maintainers
2
Versions
126
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@roomservice/browser - npm Package Compare versions

Comparing version 3.0.0-6 to 3.0.0-7

256

dist/browser.cjs.development.js

@@ -15,3 +15,2 @@ 'use strict';

var DOCS_URL = 'https://super.roomservice.dev/docs';
var PRESENCE_URL = 'https://super.roomservice.dev/presence';

@@ -267,8 +266,2 @@ function _defineProperties(target, props) {

function delay(ms) {
return new Promise(function (resolve) {
return setTimeout(resolve, ms);
});
}
var fetchSession = function fetchSession(strategy, ctx, room, document) {

@@ -377,3 +370,5 @@ try {

})).then(function (res) {
return Promise.resolve(res.json());
return Promise.resolve(res.json()).then(function (doc) {
return doc.body;
});
});

@@ -384,5 +379,5 @@ } catch (e) {

};
var fetchPresence = function fetchPresence(url, token, roomID, key) {
var fetchPresence = function fetchPresence(url, token, roomID) {
try {
return Promise.resolve(fetch(url + '/' + roomID + '/' + encodeURIComponent(key), {
return Promise.resolve(fetch(url + '/' + roomID, {
headers: {

@@ -394,12 +389,14 @@ Authorization: 'Bearer: ' + token

// Parse JSON values
for (var k in doc) {
if (typeof doc[k].value === 'string') {
var json = void 0;
for (var key in Object.keys(doc)) {
for (var actor in Object.keys(doc[key])) {
if (typeof doc[key][actor].value === 'string') {
var json = void 0;
try {
json = JSON.parse(doc[k].value);
} catch (err) {}
try {
json = JSON.parse(doc[key][actor].value);
} catch (err) {}
if (json) {
doc[k].value = json;
if (json) {
doc[key][actor].value = json;
}
}

@@ -416,3 +413,23 @@ }

};
var fetchBootstrapState = function fetchBootstrapState(props) {
try {
return Promise.resolve(Promise.all([fetchPresence(props.url, props.token, props.roomID), fetchDocument(props.url, props.token, props.docID)])).then(function (_ref) {
var allPresence = _ref[0],
documentCheckpoint = _ref[1];
return {
presence: allPresence,
document: documentCheckpoint
};
});
} catch (e) {
return Promise.reject(e);
}
};
function delay(ms) {
return new Promise(function (resolve) {
return setTimeout(resolve, ms);
});
}
var openWS = function openWS(url) {

@@ -453,3 +470,3 @@ try {

this.wsFactory = params.wsFactory || openWS;
this.documentFetch = params.documentFetch || fetchDocument;
this.bootstrapFetch = params.bootstrapFetch || fetchBootstrapState;
this.wsLoop();

@@ -497,7 +514,10 @@ }

return Promise.resolve(_this2.once('room:joined')).then(function () {
return Promise.resolve(_this2.documentFetch(_this2.docsURL, _this2.session.token, _this2.session.docID)).then(function (_ref) {
var body = _ref.body;
return Promise.resolve(_this2.bootstrapFetch({
docID: _this2.session.docID,
roomID: _this2.session.roomID,
url: _this2.docsURL,
token: _this2.session.token
})).then(function (bootstrapState) {
_this2.dispatcher.bootstrap(bootstrapState);
_this2.dispatcher.bootstrap(body);
return ws;

@@ -733,3 +753,3 @@ });

_proto.bootstrap = function bootstrap(checkpoint) {
core.ListInterpreter.importFromRawCheckpoint(this.store, checkpoint, this.meta.listID);
core.ListInterpreter.importFromRawCheckpoint(this.store, checkpoint.document, this.meta.listID);
};

@@ -839,3 +859,3 @@

_proto.bootstrap = function bootstrap(checkpoint) {
core.MapInterpreter.importFromRawCheckpoint(this.store, checkpoint, this.meta.mapID);
core.MapInterpreter.importFromRawCheckpoint(this.store, checkpoint.document, this.meta.mapID);
};

@@ -948,3 +968,3 @@

this.actor = props.actor;
this.token = props.token;
this.key = props.key;
this.cache = {};

@@ -958,33 +978,39 @@ this.bus = props.bus;

this.sendPres = throttleByFirstArgument(sendPres, 40);
this.bootstrap(props.checkpoint);
}
var _proto = InnerPresenceClient.prototype;
_proto.bootstrap = function bootstrap(checkpoint) {
this.cache = _extends({}, this.cache, checkpoint.presence[this.key] || {});
}
/**
* Gets all values for an identifier, organized by user id.
* @param key the identifier. Ex: "position"
* Gets all values for the presence key this client was created with,
* organized by user id.
*/
;
_proto.getAll = function getAll() {
// only initialize non-present values so we don't lose actors not present in this checkpoint
return this.withoutExpired();
}
/**
* Gets the current user's value.
*/
;
var _proto = InnerPresenceClient.prototype;
_proto.getMine = function getMine() {
var _this$actor;
_proto.getAll = function getAll(key) {
try {
var _this3 = this;
return Promise.resolve(fetchPresence(PRESENCE_URL, _this3.token, _this3.roomID, key)).then(function (val) {
// only initialize non-present values so we don't lose actors not present in this checkpoint
_this3.cache[key] = _extends({}, val, _this3.cache[key] || {});
return _this3.withoutExpired(key);
});
} catch (e) {
return Promise.reject(e);
}
return (_this$actor = (this.cache || {})[this.actor]) === null || _this$actor === void 0 ? void 0 : _this$actor.value;
};
_proto.withoutExpired = function withoutExpired(key) {
_proto.withoutExpired = function withoutExpired() {
var result = {};
for (var actor in this.cache[key]) {
var obj = this.cache[key][actor];
for (var actor in this.cache) {
var obj = this.cache[actor];
if (new Date() > obj.expAt) {
delete this.cache[key][actor];
delete this.cache[actor];
continue;

@@ -1004,7 +1030,7 @@ }

for (var a in this.cache[key]) {
var obj = this.cache[key][a];
var obj = this.cache[a];
if (!obj) continue; // remove this actor
if (a === actor && this.cache[key][a]) {
delete this.cache[key][a];
if (a === actor && this.cache[a]) {
delete this.cache[a];
continue;

@@ -1015,3 +1041,3 @@ } // Remove expired

if (new Date() > obj.expAt) {
delete this.cache[key][a];
delete this.cache[a];
continue;

@@ -1025,33 +1051,27 @@ }

return result;
} // Deprecated
;
}
/**
* @param key
* @param value Any arbitrary object, string, boolean, or number.
* @param exp (Optional) Expiration time in seconds
*/
_proto.set = function set(key, value, exp) {
;
_proto.set = function set(value, exp) {
var addition = exp ? exp : 60; // Convert to unix + add seconds
var expAt = Math.round(new Date().getTime() / 1000) + addition;
this.sendPres(key, {
this.sendPres(this.key, {
room: this.roomID,
key: key,
key: this.key,
value: JSON.stringify(value),
expAt: expAt
});
if (!this.cache[key]) {
this.cache[key] = {};
}
this.cache[key][this.actor] = {
this.cache[this.actor] = {
value: value,
expAt: new Date(expAt * 1000)
};
var result = this.withoutExpired(key);
var result = this.withoutExpired();
this.bus.publish({
key: key,
valuesByActor: result
key: this.key,
valuesByUser: result
});

@@ -1067,3 +1087,3 @@ return result;

if (type === 'presence:expire') {
var foo = this.withoutExpired(body.key);
var foo = this.withoutExpired();
return foo;

@@ -1079,19 +1099,6 @@ }

};
if (!this.cache[body.key]) {
this.cache[body.key] = {};
}
this.cache[body.key][body.from] = obj;
return this.withoutExpired(body.key);
this.cache[body.from] = obj;
return this.withoutExpired();
};
_createClass(InnerPresenceClient, [{
key: "me",
get: function get() {
console.warn('presence.me() is deprecated and will be removed in a future version!');
return this.actor;
}
}]);
return InnerPresenceClient;

@@ -1144,7 +1151,11 @@ }();

return Promise.resolve(fetchSession(params.authStrategy, params.authCtx, params.room, params.document)).then(function (session) {
return Promise.resolve(fetchDocument(params.docsURL, session.token, session.docID)).then(function (_ref2) {
var body = _ref2.body;
return Promise.resolve(fetchBootstrapState({
url: params.docsURL,
token: session.token,
docID: session.docID,
roomID: session.roomID
})).then(function (bootstrapState) {
var roomClient = new RoomClient({
actor: session.guestReference,
checkpoint: body,
bootstrapState: bootstrapState,
token: session.token,

@@ -1170,2 +1181,3 @@ roomID: session.roomID,

function RoomClient(params) {
this.presenceClients = {};
this.listClients = {};

@@ -1189,7 +1201,6 @@ this.mapClients = {};

});
this.token = params.token;
this.roomID = params.roomID;
this.docID = params.checkpoint.id;
this.docID = params.bootstrapState.document.id;
this.actor = params.actor;
this.checkpoint = params.checkpoint;
this.bootstrapState = params.bootstrapState;
} // impl WebsocketDispatch

@@ -1223,4 +1234,4 @@

_proto.bootstrap = function bootstrap(checkpoint) {
this.checkpoint = checkpoint;
_proto.bootstrap = function bootstrap(state) {
this.bootstrapState = state;

@@ -1230,3 +1241,3 @@ for (var _i = 0, _Object$entries = Object.entries(this.listClients); _i < _Object$entries.length; _i++) {

client = _Object$entries$_i[1];
client.bootstrap(checkpoint);
client.bootstrap(state);
}

@@ -1238,5 +1249,12 @@

_client.bootstrap(checkpoint);
_client.bootstrap(state);
}
for (var _i3 = 0, _Object$entries3 = Object.entries(this.presenceClients); _i3 < _Object$entries3.length; _i3++) {
var _Object$entries3$_i = _Object$entries3[_i3],
_client2 = _Object$entries3$_i[1];
_client2.bootstrap(state);
}
this.queueIncomingCmds = false;

@@ -1269,3 +1287,3 @@

if (core.vsReader(atob).isOlderVS(body.vs, this.checkpoint.vs)) {
if (core.vsReader(atob).isOlderVS(body.vs, this.bootstrapState.document.vs)) {
return;

@@ -1296,10 +1314,10 @@ } // Ignore validated commands

if (body.room !== this.roomID) return;
var client = this.presence();
var newClient = client.dangerouslyUpdateClientDirectly('room:rm_guest', body);
for (var _i3 = 0, _Object$entries3 = Object.entries(this.presenceCallbacksByKey); _i3 < _Object$entries3.length; _i3++) {
var _Object$entries3$_i = _Object$entries3[_i3],
cbs = _Object$entries3$_i[1];
for (var _i4 = 0, _Object$entries4 = Object.entries(this.presenceClients); _i4 < _Object$entries4.length; _i4++) {
var _Object$entries4$_i = _Object$entries4[_i4],
key = _Object$entries4$_i[0],
presenceClient = _Object$entries4$_i[1];
var newClient = presenceClient.dangerouslyUpdateClientDirectly('room:rm_guest', body);
for (var _iterator2 = _createForOfIteratorHelperLoose(cbs), _step2; !(_step2 = _iterator2()).done;) {
for (var _iterator2 = _createForOfIteratorHelperLoose(this.presenceCallbacksByKey[key] || []), _step2; !(_step2 = _iterator2()).done;) {
var cb = _step2.value;

@@ -1344,4 +1362,4 @@ cb(newClient, body.guest);

if (body.from === this.actor) return;
var client = this.presence();
var key = body.key;
var client = this.presence(key);
var now = new Date().getTime() / 1000;

@@ -1401,3 +1419,3 @@ var secondsTillTimeout = body.expAt - now;

var l = new InnerListClient({
checkpoint: this.checkpoint,
checkpoint: this.bootstrapState.document,
roomID: this.roomID,

@@ -1420,3 +1438,3 @@ docID: this.docID,

if (!this.checkpoint.lists[name]) {
if (!this.bootstrapState.document.lists[name]) {
this.ws.send('doc:cmd', {

@@ -1427,3 +1445,3 @@ args: ['lcreate', this.docID, name],

this.checkpoint.lists[name] = {
this.bootstrapState.document.lists[name] = {
afters: [],

@@ -1451,3 +1469,3 @@ ids: [],

var m = new InnerMapClient({
checkpoint: this.checkpoint,
checkpoint: this.bootstrapState.document,
roomID: this.roomID,

@@ -1470,3 +1488,3 @@ docID: this.docID,

if (!this.checkpoint.maps[name]) {
if (!this.bootstrapState.document.maps[name]) {
this.ws.send('doc:cmd', {

@@ -1481,7 +1499,7 @@ args: ['mcreate', this.docID, name],

_proto.presence = function presence() {
_proto.presence = function presence(key) {
var _this4 = this;
if (this.InnerPresenceClient) {
return this.InnerPresenceClient;
if (this.presenceClients[key]) {
return this.presenceClients[key];
}

@@ -1493,10 +1511,11 @@

var cb = _step9.value;
cb(body.valuesByActor, _this4.actor);
cb(body.valuesByUser, _this4.actor);
}
});
var p = new InnerPresenceClient({
checkpoint: this.bootstrapState,
roomID: this.roomID,
ws: this.ws,
actor: this.actor,
token: this.token,
key: key,
bus: bus

@@ -1506,3 +1525,3 @@ });

try {
this.InnerPresenceClient = p;
this.presenceClients[key] = p;
} catch (err) {

@@ -1512,9 +1531,9 @@ throw new Error("Don't Freeze State. See more: https://err.sh/getroomservice/browser/dont-freeze");

return this.InnerPresenceClient;
return this.presenceClients[key];
};
_proto.subscribe = function subscribe(obj, onChangeFnOrString, onChangeFn) {
_proto.subscribe = function subscribe(obj, onChangeFn) {
// Presence handler
if (typeof onChangeFnOrString === 'string') {
return this.subscribePresence(obj, onChangeFnOrString, onChangeFn);
if (obj instanceof InnerPresenceClient) {
return this.subscribePresence(obj, onChangeFn);
} // create new closure so fns can be subscribed/unsubscribed multiple times

@@ -1524,3 +1543,3 @@

var cb = function cb(obj, from) {
onChangeFnOrString(obj, from);
onChangeFn(obj, from);
};

@@ -1538,4 +1557,4 @@

if (obj instanceof InnerListClient) {
var _client2 = obj;
objID = _client2.id;
var _client3 = obj;
objID = _client3.id;
this.listCallbacksByObjID[objID] = this.listCallbacksByObjID[objID] || [];

@@ -1551,3 +1570,3 @@ this.listCallbacksByObjID[objID].push(cb);

_proto.subscribePresence = function subscribePresence(obj, key, onChangeFn) {
_proto.subscribePresence = function subscribePresence(obj, onChangeFn) {
!obj ? invariant(false, 'subscribe() expects the first argument to not be undefined.') : void 0; // create new closure so fns can be subscribed/unsubscribed multiple times

@@ -1561,2 +1580,3 @@

var key = obj.key;
this.presenceCallbacksByKey[key] = this.presenceCallbacksByKey[key] || [];

@@ -1563,0 +1583,0 @@ this.presenceCallbacksByKey[key].push(cb);

@@ -1,2 +0,2 @@

"use strict";Object.defineProperty(exports,"__esModule",{value:!0});var e,t=(e=require("tiny-invariant"))&&"object"==typeof e&&"default"in e?e.default:e,r=require("@roomservice/core"),n="https://super.roomservice.dev/docs";function o(e,t){for(var r=0;r<t.length;r++){var n=t[r];n.enumerable=n.enumerable||!1,n.configurable=!0,"value"in n&&(n.writable=!0),Object.defineProperty(e,n.key,n)}}function i(e,t,r){return t&&o(e.prototype,t),r&&o(e,r),e}function s(){return(s=Object.assign||function(e){for(var t=1;t<arguments.length;t++){var r=arguments[t];for(var n in r)Object.prototype.hasOwnProperty.call(r,n)&&(e[n]=r[n])}return e}).apply(this,arguments)}function c(e,t){(null==t||t>e.length)&&(t=e.length);for(var r=0,n=new Array(t);r<t;r++)n[r]=e[r];return n}function u(e,t){var r;if("undefined"==typeof Symbol||null==e[Symbol.iterator]){if(Array.isArray(e)||(r=function(e,t){if(e){if("string"==typeof e)return c(e,void 0);var r=Object.prototype.toString.call(e).slice(8,-1);return"Object"===r&&e.constructor&&(r=e.constructor.name),"Map"===r||"Set"===r?Array.from(e):"Arguments"===r||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(r)?c(e,void 0):void 0}}(e))||t&&e&&"number"==typeof e.length){r&&(e=r);var n=0;return function(){return n>=e.length?{done:!0}:{done:!1,value:e[n++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(r=e[Symbol.iterator]()).next.bind(r)}const a=function(){function e(){}return e.prototype.then=function(t,r){const n=new e,o=this.s;if(o){const e=1&o?t:r;if(e){try{h(n,1,e(this.v))}catch(e){h(n,2,e)}return n}return this}return this.o=function(e){try{const o=e.v;1&e.s?h(n,1,t?t(o):o):r?h(n,1,r(o)):h(n,2,o)}catch(e){h(n,2,e)}},n},e}();function h(e,t,r){if(!e.s){if(r instanceof a){if(!r.s)return void(r.o=h.bind(null,e,t));1&t&&(t=r.s),r=r.v}if(r&&r.then)return void r.then(h.bind(null,e,t),h.bind(null,e,2));e.s=t,e.v=r;const n=e.o;n&&n(e)}}function l(e){return e instanceof a&&1&e.s}function d(e,t,r){for(var n;;){var o=e();if(l(o)&&(o=o.v),!o)return i;if(o.then){n=0;break}var i=r();if(i&&i.then){if(!l(i)){n=1;break}i=i.s}if(t){var s=t();if(s&&s.then&&!l(s)){n=2;break}}}var c=new a,u=h.bind(null,c,2);return(0===n?o.then(m):1===n?i.then(d):s.then(f)).then(void 0,u),c;function d(n){i=n;do{if(t&&(s=t())&&s.then&&!l(s))return void s.then(f).then(void 0,u);if(!(o=e())||l(o)&&!o.v)return void h(c,1,i);if(o.then)return void o.then(m).then(void 0,u);l(i=r())&&(i=i.v)}while(!i||!i.then);i.then(d).then(void 0,u)}function m(e){e?(i=r())&&i.then?i.then(d).then(void 0,u):d(i):h(c,1,i)}function f(){(o=e())?o.then?o.then(m).then(void 0,u):m(o):h(c,1,i)}}function m(e){return new Promise((function(t){return setTimeout(t,e)}))}"undefined"!=typeof Symbol&&(Symbol.iterator||(Symbol.iterator=Symbol("Symbol.iterator"))),"undefined"!=typeof Symbol&&(Symbol.asyncIterator||(Symbol.asyncIterator=Symbol("Symbol.asyncIterator")));var f=function(e,t,r){try{return Promise.resolve(fetch(e+"/"+r,{headers:{Authorization:"Bearer: "+t}})).then((function(e){return Promise.resolve(e.json())}))}catch(e){return Promise.reject(e)}},p=function(e){try{return Promise.resolve(new Promise((function(t,r){var n=new WebSocket(e);n.onopen=function(){t(n)},n.onerror=function(e){r(e)}})))}catch(e){return Promise.reject(e)}},v=["doc:fwd","presence:fwd","room:rm_guest"],b=function(){function e(e){this.callbacks={},this.lastTime=0,this.msgsThisMilisecond=0,this.docCmdSendQueue=[],this.presenceCmdSendQueue=new Map,this.dispatcher=e.dispatcher,this.wsURL=e.wsURL,this.docsURL=e.docsURL,this.room=e.room,this.session=e.session,this.wsFactory=e.wsFactory||p,this.documentFetch=e.documentFetch||f,this.wsLoop()}var t=e.prototype;return t.close=function(){this.currentConn&&(this.currentConn.onmessage=null,this.currentConn.onclose=null,this.currentConn.close(),this.currentConn=void 0),this.pendingConn&&(this.pendingConn=void 0),this.dispatcher.startQueueingCmds()},t.connectAndAuth=function(){try{var e=this;return Promise.resolve(e.wsFactory(e.wsURL)).then((function(t){return t.onmessage=function(t){var r=JSON.parse(t.data);e.dispatch(r.type,r.body)},t.onclose=function(){return e.close()},Promise.resolve(t).then((function(t){try{return t.send(e.serializeMsg("guest:authenticate",e.session.token)),Promise.resolve(e.once("guest:authenticated")).then((function(){return t.send(e.serializeMsg("room:join",e.room)),Promise.resolve(e.once("room:joined")).then((function(){return Promise.resolve(e.documentFetch(e.docsURL,e.session.token,e.session.docID)).then((function(r){return e.dispatcher.bootstrap(r.body),t}))}))}))}catch(e){return Promise.reject(e)}}))}))}catch(e){return Promise.reject(e)}},t.conn=function(){try{var e=this;return e.currentConn?Promise.resolve(e.currentConn):(e.pendingConn||(e.close(),e.pendingConn=function(){try{var t=!1,r=0;return Promise.resolve(d((function(){return!t}),void 0,(function(){var n=r*(Math.random()+1)/2;return Promise.resolve(m(n)).then((function(){return r=Math.min(2*r+100,6e4),function(r,n){try{var o=Promise.resolve(e.connectAndAuth()).then((function(r){return e.currentConn=r,e.pendingConn=void 0,t=!0,r}))}catch(e){return n(e)}return o&&o.then?o.then(void 0,n):o}(0,(function(e){console.error("Connection to RoomService failed with",e,"\nRetrying...")}))}))})))}catch(e){return Promise.reject(e)}}()),Promise.resolve(e.pendingConn))}catch(e){return Promise.reject(e)}},t.wsLoop=function(){try{var e=this,t=d((function(){return!0}),void 0,(function(){return Promise.resolve(e.conn()).then((function(){return e.processSendQueue(),Promise.resolve(m(1e3)).then((function(){}))}))}));return Promise.resolve(t&&t.then?t.then((function(){})):void 0)}catch(e){return Promise.reject(e)}},t.timestamp=function(){var e=Date.now();return e===this.lastTime?this.msgsThisMilisecond++:(this.lastTime=e,this.msgsThisMilisecond=0),e+":"+this.msgsThisMilisecond},t.serializeMsg=function(e,t){var r=this.timestamp();return JSON.stringify({type:e,ts:r,ver:0,body:t})},t.send=function(e,t){if("doc:cmd"==e){if(this.docCmdSendQueue.length>=1e4)throw"RoomService send queue full";var r=this.serializeMsg(e,t);this.docCmdSendQueue.push(r)}if("presence:cmd"==e){var n=this.serializeMsg(e,t);this.presenceCmdSendQueue.set(t.key,n)}this.processSendQueue()},t.processSendQueue=function(){if(this.currentConn)try{for(;this.presenceCmdSendQueue.size>0;){var e=this.presenceCmdSendQueue.entries().next();if(e){var t=e.value,r=t[0];this.currentConn.send(t[1]),this.presenceCmdSendQueue.delete(r)}}for(;this.docCmdSendQueue.length>0;)this.currentConn.send(this.docCmdSendQueue[0]),this.docCmdSendQueue.splice(0,1)}catch(e){console.error(e)}},t.bind=function(e,t){return this.callbacks[e]=this.callbacks[e]||[],this.callbacks[e].push(t),t},t.unbind=function(e,t){this.callbacks[e]=this.callbacks[e].filter((function(e){return e!==t}))},t.dispatch=function(e,t){"error"==e&&console.error(t);var r=this.callbacks[e];if(r)for(var n=0;n<r.length;n++)r[n](t);v.includes(e)&&this.dispatcher.forwardCmd(e,t)},t.once=function(e){try{var t,r=this;return Promise.race([new Promise((function(e,t){return setTimeout((function(){return t("timeout")}),2e3)})),new Promise((function(n){t=r.bind(e,(function(e){n(e)}))}))]).then((function(){t&&r.unbind(e,t)}))}catch(e){return Promise.reject(e)}},e}(),y=function(){function e(e){this.roomID=e.roomID,this.ws=e.ws,this.bus=e.bus,this.actor=e.actor,this.id=e.listID;var n=r.ListInterpreter.newList(e.docID,e.listID,e.actor),o=n.store;this.meta=n.meta,this.store=o,e.checkpoint.lists[e.listID]||t(!1),r.ListInterpreter.importFromRawCheckpoint(this.store,e.checkpoint,this.meta.listID)}var n=e.prototype;return n.bootstrap=function(e){r.ListInterpreter.importFromRawCheckpoint(this.store,e,this.meta.listID)},n.sendCmd=function(e){this.ws.send("doc:cmd",{room:this.roomID,args:e}),this.bus.publish({args:e,from:this.actor})},n.clone=function(){return Object.assign(Object.create(Object.getPrototypeOf(this)),this)},n.dangerouslyUpdateClientDirectly=function(e){return r.ListInterpreter.validateCommand(this.meta,e),r.ListInterpreter.applyCommand(this.store,e),this.clone()},n.get=function(e){return r.ListInterpreter.get(this.store,e)},n.set=function(e,t){var n=r.ListInterpreter.runSet(this.store,this.meta,e,t);return this.sendCmd(n),this.clone()},n.delete=function(e){var t=r.ListInterpreter.runDelete(this.store,this.meta,e);return t?(this.sendCmd(t),this.clone()):this.clone()},n.insertAfter=function(e,t){return this.insertAt(e+1,t)},n.insertAt=function(e,t){var n=r.ListInterpreter.runInsertAt(this.store,this.meta,e,t);return this.sendCmd(n),this.clone()},n.push=function(){for(var e=arguments.length,t=new Array(e),n=0;n<e;n++)t[n]=arguments[n];for(var o,i=r.ListInterpreter.runPush.apply(r.ListInterpreter,[this.store,this.meta].concat(t)),s=u(i);!(o=s()).done;){var c=o.value;this.sendCmd(c)}return this},n.map=function(e){return r.ListInterpreter.map(this.store,e)},n.toArray=function(){return r.ListInterpreter.toArray(this.store)},e}(),C=function(){function e(e){this.roomID=e.roomID,this.ws=e.ws,this.bus=e.bus,this.actor=e.actor;var t=r.MapInterpreter.newMap(e.docID,e.mapID),n=t.meta;this.store=t.store,this.meta=n,r.MapInterpreter.importFromRawCheckpoint(this.store,e.checkpoint,this.meta.mapID)}var t=e.prototype;return t.bootstrap=function(e){r.MapInterpreter.importFromRawCheckpoint(this.store,e,this.meta.mapID)},t.sendCmd=function(e){this.ws.send("doc:cmd",{room:this.roomID,args:e}),this.bus.publish({from:this.actor,args:e})},t.clone=function(){return Object.assign(Object.create(Object.getPrototypeOf(this)),this)},t.dangerouslyUpdateClientDirectly=function(e){return r.MapInterpreter.validateCommand(this.meta,e),r.MapInterpreter.applyCommand(this.store,e),this.clone()},t.get=function(e){return this.store[e]},t.set=function(e,t){var n=r.MapInterpreter.runSet(this.store,this.meta,e,t);return this.sendCmd(n),this.clone()},t.toObject=function(){for(var e,t={},r=u(this.keys);!(e=r()).done;){var n=e.value;t[n]=this.get(n)}return t},t.delete=function(e){var t=r.MapInterpreter.runDelete(this.store,this.meta,e);return this.sendCmd(t),this.clone()},i(e,[{key:"id",get:function(){return this.meta.mapID}},{key:"keys",get:function(){return Object.keys(this.store)}}]),e}(),I=function(){function e(e){var t=this;this.roomID=e.roomID,this.ws=e.ws,this.actor=e.actor,this.token=e.token,this.cache={},this.bus=e.bus,this.sendPres=function(e,t,r){void 0===r&&(r=!1);var n={},o=!0;return function(){var t=arguments,i=this,s=r&&o,c=function(){e.apply(i,t),n[t[0]]=null};s&&(o=!1,c()),n[arguments[0]]||(n[arguments[0]]=setTimeout(c,40))}}((function(e,r){t.ws.send("presence:cmd",r)}))}var t=e.prototype;return t.getAll=function(e){try{var t=this;return Promise.resolve(function(e,t,r,n){try{return Promise.resolve(fetch("https://super.roomservice.dev/presence/"+r+"/"+encodeURIComponent(n),{headers:{Authorization:"Bearer: "+t}})).then((function(e){return Promise.resolve(e.json()).then((function(e){for(var t in e)if("string"==typeof e[t].value){var r=void 0;try{r=JSON.parse(e[t].value)}catch(e){}r&&(e[t].value=r)}return e}))}))}catch(e){return Promise.reject(e)}}(0,t.token,t.roomID,e)).then((function(r){return t.cache[e]=s({},r,t.cache[e]||{}),t.withoutExpired(e)}))}catch(e){return Promise.reject(e)}},t.withoutExpired=function(e){var t={};for(var r in this.cache[e]){var n=this.cache[e][r];new Date>n.expAt?delete this.cache[e][r]:t[r]=n.value}return t},t.withoutActorOrExpired=function(e){var t={};for(var r in this.cache)for(var n in this.cache[r]){var o=this.cache[r][n];o&&(n===e&&this.cache[r][n]||new Date>o.expAt?delete this.cache[r][n]:t[n]=o.value)}return t},t.set=function(e,t,r){var n=r||60,o=Math.round((new Date).getTime()/1e3)+n;this.sendPres(e,{room:this.roomID,key:e,value:JSON.stringify(t),expAt:o}),this.cache[e]||(this.cache[e]={}),this.cache[e][this.actor]={value:t,expAt:new Date(1e3*o)};var i=this.withoutExpired(e);return this.bus.publish({key:e,valuesByActor:i}),i},t.dangerouslyUpdateClientDirectly=function(e,t){if("room:rm_guest"===e)return this.withoutActorOrExpired(t.guest);if("presence:expire"===e)return this.withoutExpired(t.key);if(t.room!==this.roomID)return!1;if(t.from===this.actor)return!1;var r={expAt:new Date(1e3*t.expAt),value:JSON.parse(t.value)};return this.cache[t.key]||(this.cache[t.key]={}),this.cache[t.key][t.from]=r,this.withoutExpired(t.key)},i(e,[{key:"me",get:function(){return console.warn("presence.me() is deprecated and will be removed in a future version!"),this.actor}}]),e}(),g=function(){function e(){this.isPublishing=!1,this.subs=new Set}var t=e.prototype;return t.unsubscribe=function(e){this.subs.delete(e)},t.subscribe=function(e){return this.subs.add(e),e},t.publish=function(e){if(this.isPublishing)throw new Error("Infinite loop detected, see more: See more: https://err.sh/getroomservice/browser/infinite-loop");this.isPublishing=!0,this.subs.forEach((function(t){t(e)})),this.isPublishing=!1},e}(),w=["mcreate","mput","mputref","mdel"],D=["lcreate","lins","linsref","lput","lputref","ldel"],k=function(){function e(e){this.listClients={},this.mapClients={},this.expires={},this.queueIncomingCmds=!0,this.cmdQueue=[],this.mapCallbacksByObjID={},this.listCallbacksByObjID={},this.presenceCallbacksByKey={},this.ws=new b({dispatcher:this,wsURL:e.wsURL,docsURL:e.docsURL,room:e.roomID,session:e.session}),this.token=e.token,this.roomID=e.roomID,this.docID=e.checkpoint.id,this.actor=e.actor,this.checkpoint=e.checkpoint}var n=e.prototype;return n.forwardCmd=function(e,t){this.queueIncomingCmds?this.cmdQueue.push([e,t]):this.processCmd(e,t)},n.processCmd=function(e,t){"doc:fwd"==e&&"args"in t&&this.dispatchDocCmd(t),"presence:fwd"==e&&"expAt"in t&&this.dispatchPresenceCmd(t),"room:rm_guest"==e&&"guest"in t&&this.dispatchRmGuest(t)},n.bootstrap=function(e){this.checkpoint=e;for(var t=0,r=Object.entries(this.listClients);t<r.length;t++)r[t][1].bootstrap(e);for(var n=0,o=Object.entries(this.mapClients);n<o.length;n++)o[n][1].bootstrap(e);this.queueIncomingCmds=!1;for(var i,s=u(this.cmdQueue);!(i=s()).done;){var c=i.value;this.processCmd(c[0],c[1])}this.cmdQueue.length=0},n.startQueueingCmds=function(){this.queueIncomingCmds=!0},n.dispatchDocCmd=function(e){if(e.room===this.roomID)if(!e.args||e.args.length<3)console.error("Unexpected command: ",e.args);else if(!r.vsReader(atob).isOlderVS(e.vs,this.checkpoint.vs)&&e.from!==this.actor){var t=[e.args[0],e.args[1],e.args[2]],n=t[0],o=t[2];t[1]===this.docID&&(w.includes(n)?this.dispatchMapCmd(o,e):D.includes(n)?this.dispatchListCmd(o,e):console.warn("Unhandled Room Service doc:fwd command: "+n+". Consider updating the Room Service client."))}},n.dispatchRmGuest=function(e){if(e.room===this.roomID)for(var t=this.presence().dangerouslyUpdateClientDirectly("room:rm_guest",e),r=0,n=Object.entries(this.presenceCallbacksByKey);r<n.length;r++)for(var o,i=u(n[r][1]);!(o=i()).done;)(0,o.value)(t,e.guest)},n.dispatchMapCmd=function(e,t){this.mapClients[e]||this.createMapLocally(e);for(var r,n=this.mapClients[e].dangerouslyUpdateClientDirectly(t.args),o=u(this.mapCallbacksByObjID[e]||[]);!(r=o()).done;)(0,r.value)(n.toObject(),t.from)},n.dispatchListCmd=function(e,t){this.listClients[e]||this.createListLocally(e);for(var r,n=this.listClients[e].dangerouslyUpdateClientDirectly(t.args),o=u(this.listCallbacksByObjID[e]||[]);!(r=o()).done;)(0,r.value)(n.toArray(),t.from)},n.dispatchPresenceCmd=function(e){var t=this;if(e.room===this.roomID&&e.from!==this.actor){var r=this.presence(),n=e.key,o=(new Date).getTime()/1e3,i=e.expAt-o;if(!(i<0)){if(i<43200){this.expires[n]&&clearTimeout(this.expires[n]);var s=setTimeout((function(){var o=r.dangerouslyUpdateClientDirectly("presence:expire",{key:e.key});if(o)for(var i,s=u(null!==(c=t.presenceCallbacksByKey[n])&&void 0!==c?c:[]);!(i=s()).done;){var c;(0,i.value)(o,e.from)}}),1e3*i);this.expires[n]=s}var c=r.dangerouslyUpdateClientDirectly("presence:fwd",e);if(c)for(var a,h=u(null!==(l=this.presenceCallbacksByKey[n])&&void 0!==l?l:[]);!(a=h()).done;){var l;(0,a.value)(c,e.from)}}}},n.createListLocally=function(e){var t=this,r=new g;r.subscribe((function(r){for(var n,o=t.listClients[e],i=u(t.listCallbacksByObjID[e]||[]);!(n=i()).done;)(0,n.value)(o.toArray(),r.from)}));var n=new y({checkpoint:this.checkpoint,roomID:this.roomID,docID:this.docID,listID:e,ws:this.ws,actor:this.actor,bus:r});return this.listClients[e]=n,n},n.list=function(e){return this.listClients[e]?this.listClients[e]:(this.checkpoint.lists[e]||(this.ws.send("doc:cmd",{args:["lcreate",this.docID,e],room:this.roomID}),this.checkpoint.lists[e]={afters:[],ids:[],values:[]}),this.createListLocally(e))},n.createMapLocally=function(e){var t=this,r=new g;r.subscribe((function(r){for(var n,o=t.mapClients[e],i=u(t.mapCallbacksByObjID[e]||[]);!(n=i()).done;)(0,n.value)(o.toObject(),r.from)}));var n=new C({checkpoint:this.checkpoint,roomID:this.roomID,docID:this.docID,mapID:e,ws:this.ws,bus:r,actor:this.actor});return this.mapClients[e]=n,n},n.map=function(e){return this.mapClients[e]?this.mapClients[e]:(this.checkpoint.maps[e]||this.ws.send("doc:cmd",{args:["mcreate",this.docID,e],room:this.roomID}),this.createMapLocally(e))},n.presence=function(){var e=this;if(this.InnerPresenceClient)return this.InnerPresenceClient;var t=new g;t.subscribe((function(t){for(var r,n=u(e.presenceCallbacksByKey[t.key]||[]);!(r=n()).done;)(0,r.value)(t.valuesByActor,e.actor)}));var r=new I({roomID:this.roomID,ws:this.ws,actor:this.actor,token:this.token,bus:t});try{this.InnerPresenceClient=r}catch(e){throw new Error("Don't Freeze State. See more: https://err.sh/getroomservice/browser/dont-freeze")}return this.InnerPresenceClient},n.subscribe=function(e,t,r){if("string"==typeof t)return this.subscribePresence(e,t,r);var n,o=function(e,r){t(e,r)};return e instanceof C&&(this.mapCallbacksByObjID[n=e.id]=this.mapCallbacksByObjID[n]||[],this.mapCallbacksByObjID[n].push(o)),e instanceof y&&(this.listCallbacksByObjID[n=e.id]=this.listCallbacksByObjID[n]||[],this.listCallbacksByObjID[n].push(o)),[{objID:n,fn:o}]},n.subscribePresence=function(e,r,n){e||t(!1);var o=function(e,t){n&&n(e,t)};return this.presenceCallbacksByKey[r]=this.presenceCallbacksByKey[r]||[],this.presenceCallbacksByKey[r].push(o),[{objID:r,fn:o}]},n.unsubscribe=function(e){for(var t,r=u(e);!(t=r()).done;){var n=t.value;n.objID&&(this.mapCallbacksByObjID[n.objID]=j(this.mapCallbacksByObjID[n.objID],n.fn),this.listCallbacksByObjID[n.objID]=j(this.listCallbacksByObjID[n.objID],n.fn),this.presenceCallbacksByKey[n.objID]=j(this.presenceCallbacksByKey[n.objID],n.fn))}},i(e,[{key:"me",get:function(){return this.actor}}]),e}();function j(e,t){return e?e.filter((function(e){return e!==t})):[]}var P=function(){function e(e){this.roomClients={},this.auth=e.auth,this.ctx=e.ctx||{}}return e.prototype.room=function(e){try{var t=this;return t.roomClients[e]?Promise.resolve(t.roomClients[e]):Promise.resolve(function(e){try{return Promise.resolve(function(e,t,r,n){try{var o=function(t){return i?t:Promise.resolve(fetch(e,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({resources:[{object:"document",reference:n,permission:"read_write",room:r},{object:"room",reference:r,permission:"join"}]})})).then((function(e){if(401===e.status)throw new Error("The Auth Webhook returned unauthorized.");if(200!==e.status)throw new Error("The Auth Webhook returned a status code other than 200.");return Promise.resolve(e.json()).then((function(e){var t=e.resources,r=e.token,n=e.user;if(!t||!r||!n){if("Unauthorized"===e.body)throw new Error("The Auth Webhook unexpectedly return unauthorized. You may be using an invalid API key.");throw new Error("The Auth Webhook has an incorrectly formatted JSON response.")}return{token:r,guestReference:n,docID:t.find((function(e){return"document"===e.object})).id,roomID:t.find((function(e){return"room"===e.object})).id}}))}))},i=!1,s=function(){if("function"==typeof e)return Promise.resolve(e({room:r,ctx:t})).then((function(e){if(!e.user)throw new Error("The auth function must return a 'user' key.");var t=e.resources.find((function(e){return"document"===e.object})).id,r=e.resources.find((function(e){return"room"===e.object})).id;return i=!0,{token:e.token,guestReference:e.user,docID:t,roomID:r}}))}();return Promise.resolve(s&&s.then?s.then(o):o(s))}catch(e){return Promise.reject(e)}}(e.authStrategy,e.authCtx,e.room,e.document)).then((function(t){return Promise.resolve(f(e.docsURL,t.token,t.docID)).then((function(r){return new k({actor:t.guestReference,checkpoint:r.body,token:t.token,roomID:t.roomID,docID:e.document,auth:e.authStrategy,authCtx:e.authCtx,wsURL:"wss://super.roomservice.dev/ws",docsURL:n,session:t})}))}))}catch(e){return Promise.reject(e)}}({docsURL:n,authStrategy:t.auth,authCtx:t.ctx,room:e,document:"default"})).then((function(r){return t.roomClients[e]=r,r}))}catch(e){return Promise.reject(e)}},e}();exports.RoomClient=k,exports.RoomService=P,exports.default=P;
"use strict";Object.defineProperty(exports,"__esModule",{value:!0});var t,e=(t=require("tiny-invariant"))&&"object"==typeof t&&"default"in t?t.default:t,r=require("@roomservice/core"),n="https://super.roomservice.dev/docs";function o(t,e){for(var r=0;r<e.length;r++){var n=e[r];n.enumerable=n.enumerable||!1,n.configurable=!0,"value"in n&&(n.writable=!0),Object.defineProperty(t,n.key,n)}}function s(t,e,r){return e&&o(t.prototype,e),r&&o(t,r),t}function i(){return(i=Object.assign||function(t){for(var e=1;e<arguments.length;e++){var r=arguments[e];for(var n in r)Object.prototype.hasOwnProperty.call(r,n)&&(t[n]=r[n])}return t}).apply(this,arguments)}function c(t,e){(null==e||e>t.length)&&(e=t.length);for(var r=0,n=new Array(e);r<e;r++)n[r]=t[r];return n}function a(t,e){var r;if("undefined"==typeof Symbol||null==t[Symbol.iterator]){if(Array.isArray(t)||(r=function(t,e){if(t){if("string"==typeof t)return c(t,void 0);var r=Object.prototype.toString.call(t).slice(8,-1);return"Object"===r&&t.constructor&&(r=t.constructor.name),"Map"===r||"Set"===r?Array.from(t):"Arguments"===r||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(r)?c(t,void 0):void 0}}(t))||e&&t&&"number"==typeof t.length){r&&(t=r);var n=0;return function(){return n>=t.length?{done:!0}:{done:!1,value:t[n++]}}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}return(r=t[Symbol.iterator]()).next.bind(r)}const u=function(){function t(){}return t.prototype.then=function(e,r){const n=new t,o=this.s;if(o){const t=1&o?e:r;if(t){try{h(n,1,t(this.v))}catch(t){h(n,2,t)}return n}return this}return this.o=function(t){try{const o=t.v;1&t.s?h(n,1,e?e(o):o):r?h(n,1,r(o)):h(n,2,o)}catch(t){h(n,2,t)}},n},t}();function h(t,e,r){if(!t.s){if(r instanceof u){if(!r.s)return void(r.o=h.bind(null,t,e));1&e&&(e=r.s),r=r.v}if(r&&r.then)return void r.then(h.bind(null,t,e),h.bind(null,t,2));t.s=e,t.v=r;const n=t.o;n&&n(t)}}function l(t){return t instanceof u&&1&t.s}function d(t,e,r){for(var n;;){var o=t();if(l(o)&&(o=o.v),!o)return s;if(o.then){n=0;break}var s=r();if(s&&s.then){if(!l(s)){n=1;break}s=s.s}if(e){var i=e();if(i&&i.then&&!l(i)){n=2;break}}}var c=new u,a=h.bind(null,c,2);return(0===n?o.then(m):1===n?s.then(d):i.then(f)).then(void 0,a),c;function d(n){s=n;do{if(e&&(i=e())&&i.then&&!l(i))return void i.then(f).then(void 0,a);if(!(o=t())||l(o)&&!o.v)return void h(c,1,s);if(o.then)return void o.then(m).then(void 0,a);l(s=r())&&(s=s.v)}while(!s||!s.then);s.then(d).then(void 0,a)}function m(t){t?(s=r())&&s.then?s.then(d).then(void 0,a):d(s):h(c,1,s)}function f(){(o=t())?o.then?o.then(m).then(void 0,a):m(o):h(c,1,s)}}"undefined"!=typeof Symbol&&(Symbol.iterator||(Symbol.iterator=Symbol("Symbol.iterator"))),"undefined"!=typeof Symbol&&(Symbol.asyncIterator||(Symbol.asyncIterator=Symbol("Symbol.asyncIterator")));var m=function(t,e,r){try{return Promise.resolve(fetch(t+"/"+r,{headers:{Authorization:"Bearer: "+e}})).then((function(t){return Promise.resolve(t.json()).then((function(t){return t.body}))}))}catch(t){return Promise.reject(t)}},f=function(t,e,r){try{return Promise.resolve(fetch(t+"/"+r,{headers:{Authorization:"Bearer: "+e}})).then((function(t){return Promise.resolve(t.json()).then((function(t){for(var e in Object.keys(t))for(var r in Object.keys(t[e]))if("string"==typeof t[e][r].value){var n=void 0;try{n=JSON.parse(t[e][r].value)}catch(t){}n&&(t[e][r].value=n)}return t}))}))}catch(t){return Promise.reject(t)}},p=function(t){try{return Promise.resolve(Promise.all([f(t.url,t.token,t.roomID),m(t.url,t.token,t.docID)])).then((function(t){return{presence:t[0],document:t[1]}}))}catch(t){return Promise.reject(t)}};function v(t){return new Promise((function(e){return setTimeout(e,t)}))}var b=function(t){try{return Promise.resolve(new Promise((function(e,r){var n=new WebSocket(t);n.onopen=function(){e(n)},n.onerror=function(t){r(t)}})))}catch(t){return Promise.reject(t)}},y=["doc:fwd","presence:fwd","room:rm_guest"],C=function(){function t(t){this.callbacks={},this.lastTime=0,this.msgsThisMilisecond=0,this.docCmdSendQueue=[],this.presenceCmdSendQueue=new Map,this.dispatcher=t.dispatcher,this.wsURL=t.wsURL,this.docsURL=t.docsURL,this.room=t.room,this.session=t.session,this.wsFactory=t.wsFactory||b,this.bootstrapFetch=t.bootstrapFetch||p,this.wsLoop()}var e=t.prototype;return e.close=function(){this.currentConn&&(this.currentConn.onmessage=null,this.currentConn.onclose=null,this.currentConn.close(),this.currentConn=void 0),this.pendingConn&&(this.pendingConn=void 0),this.dispatcher.startQueueingCmds()},e.connectAndAuth=function(){try{var t=this;return Promise.resolve(t.wsFactory(t.wsURL)).then((function(e){return e.onmessage=function(e){var r=JSON.parse(e.data);t.dispatch(r.type,r.body)},e.onclose=function(){return t.close()},Promise.resolve(e).then((function(e){try{return e.send(t.serializeMsg("guest:authenticate",t.session.token)),Promise.resolve(t.once("guest:authenticated")).then((function(){return e.send(t.serializeMsg("room:join",t.room)),Promise.resolve(t.once("room:joined")).then((function(){return Promise.resolve(t.bootstrapFetch({docID:t.session.docID,roomID:t.session.roomID,url:t.docsURL,token:t.session.token})).then((function(r){return t.dispatcher.bootstrap(r),e}))}))}))}catch(t){return Promise.reject(t)}}))}))}catch(t){return Promise.reject(t)}},e.conn=function(){try{var t=this;return t.currentConn?Promise.resolve(t.currentConn):(t.pendingConn||(t.close(),t.pendingConn=function(){try{var e=!1,r=0;return Promise.resolve(d((function(){return!e}),void 0,(function(){var n=r*(Math.random()+1)/2;return Promise.resolve(v(n)).then((function(){return r=Math.min(2*r+100,6e4),function(r,n){try{var o=Promise.resolve(t.connectAndAuth()).then((function(r){return t.currentConn=r,t.pendingConn=void 0,e=!0,r}))}catch(t){return n(t)}return o&&o.then?o.then(void 0,n):o}(0,(function(t){console.error("Connection to RoomService failed with",t,"\nRetrying...")}))}))})))}catch(t){return Promise.reject(t)}}()),Promise.resolve(t.pendingConn))}catch(t){return Promise.reject(t)}},e.wsLoop=function(){try{var t=this,e=d((function(){return!0}),void 0,(function(){return Promise.resolve(t.conn()).then((function(){return t.processSendQueue(),Promise.resolve(v(1e3)).then((function(){}))}))}));return Promise.resolve(e&&e.then?e.then((function(){})):void 0)}catch(t){return Promise.reject(t)}},e.timestamp=function(){var t=Date.now();return t===this.lastTime?this.msgsThisMilisecond++:(this.lastTime=t,this.msgsThisMilisecond=0),t+":"+this.msgsThisMilisecond},e.serializeMsg=function(t,e){var r=this.timestamp();return JSON.stringify({type:t,ts:r,ver:0,body:e})},e.send=function(t,e){if("doc:cmd"==t){if(this.docCmdSendQueue.length>=1e4)throw"RoomService send queue full";var r=this.serializeMsg(t,e);this.docCmdSendQueue.push(r)}if("presence:cmd"==t){var n=this.serializeMsg(t,e);this.presenceCmdSendQueue.set(e.key,n)}this.processSendQueue()},e.processSendQueue=function(){if(this.currentConn)try{for(;this.presenceCmdSendQueue.size>0;){var t=this.presenceCmdSendQueue.entries().next();if(t){var e=t.value,r=e[0];this.currentConn.send(e[1]),this.presenceCmdSendQueue.delete(r)}}for(;this.docCmdSendQueue.length>0;)this.currentConn.send(this.docCmdSendQueue[0]),this.docCmdSendQueue.splice(0,1)}catch(t){console.error(t)}},e.bind=function(t,e){return this.callbacks[t]=this.callbacks[t]||[],this.callbacks[t].push(e),e},e.unbind=function(t,e){this.callbacks[t]=this.callbacks[t].filter((function(t){return t!==e}))},e.dispatch=function(t,e){"error"==t&&console.error(e);var r=this.callbacks[t];if(r)for(var n=0;n<r.length;n++)r[n](e);y.includes(t)&&this.dispatcher.forwardCmd(t,e)},e.once=function(t){try{var e,r=this;return Promise.race([new Promise((function(t,e){return setTimeout((function(){return e("timeout")}),2e3)})),new Promise((function(n){e=r.bind(t,(function(t){n(t)}))}))]).then((function(){e&&r.unbind(t,e)}))}catch(t){return Promise.reject(t)}},t}(),I=function(){function t(t){this.roomID=t.roomID,this.ws=t.ws,this.bus=t.bus,this.actor=t.actor,this.id=t.listID;var n=r.ListInterpreter.newList(t.docID,t.listID,t.actor),o=n.store;this.meta=n.meta,this.store=o,t.checkpoint.lists[t.listID]||e(!1),r.ListInterpreter.importFromRawCheckpoint(this.store,t.checkpoint,this.meta.listID)}var n=t.prototype;return n.bootstrap=function(t){r.ListInterpreter.importFromRawCheckpoint(this.store,t.document,this.meta.listID)},n.sendCmd=function(t){this.ws.send("doc:cmd",{room:this.roomID,args:t}),this.bus.publish({args:t,from:this.actor})},n.clone=function(){return Object.assign(Object.create(Object.getPrototypeOf(this)),this)},n.dangerouslyUpdateClientDirectly=function(t){return r.ListInterpreter.validateCommand(this.meta,t),r.ListInterpreter.applyCommand(this.store,t),this.clone()},n.get=function(t){return r.ListInterpreter.get(this.store,t)},n.set=function(t,e){var n=r.ListInterpreter.runSet(this.store,this.meta,t,e);return this.sendCmd(n),this.clone()},n.delete=function(t){var e=r.ListInterpreter.runDelete(this.store,this.meta,t);return e?(this.sendCmd(e),this.clone()):this.clone()},n.insertAfter=function(t,e){return this.insertAt(t+1,e)},n.insertAt=function(t,e){var n=r.ListInterpreter.runInsertAt(this.store,this.meta,t,e);return this.sendCmd(n),this.clone()},n.push=function(){for(var t=arguments.length,e=new Array(t),n=0;n<t;n++)e[n]=arguments[n];for(var o,s=r.ListInterpreter.runPush.apply(r.ListInterpreter,[this.store,this.meta].concat(e)),i=a(s);!(o=i()).done;){var c=o.value;this.sendCmd(c)}return this},n.map=function(t){return r.ListInterpreter.map(this.store,t)},n.toArray=function(){return r.ListInterpreter.toArray(this.store)},t}(),g=function(){function t(t){this.roomID=t.roomID,this.ws=t.ws,this.bus=t.bus,this.actor=t.actor;var e=r.MapInterpreter.newMap(t.docID,t.mapID),n=e.meta;this.store=e.store,this.meta=n,r.MapInterpreter.importFromRawCheckpoint(this.store,t.checkpoint,this.meta.mapID)}var e=t.prototype;return e.bootstrap=function(t){r.MapInterpreter.importFromRawCheckpoint(this.store,t.document,this.meta.mapID)},e.sendCmd=function(t){this.ws.send("doc:cmd",{room:this.roomID,args:t}),this.bus.publish({from:this.actor,args:t})},e.clone=function(){return Object.assign(Object.create(Object.getPrototypeOf(this)),this)},e.dangerouslyUpdateClientDirectly=function(t){return r.MapInterpreter.validateCommand(this.meta,t),r.MapInterpreter.applyCommand(this.store,t),this.clone()},e.get=function(t){return this.store[t]},e.set=function(t,e){var n=r.MapInterpreter.runSet(this.store,this.meta,t,e);return this.sendCmd(n),this.clone()},e.toObject=function(){for(var t,e={},r=a(this.keys);!(t=r()).done;){var n=t.value;e[n]=this.get(n)}return e},e.delete=function(t){var e=r.MapInterpreter.runDelete(this.store,this.meta,t);return this.sendCmd(e),this.clone()},s(t,[{key:"id",get:function(){return this.meta.mapID}},{key:"keys",get:function(){return Object.keys(this.store)}}]),t}(),D=function(){function t(t){var e=this;this.roomID=t.roomID,this.ws=t.ws,this.actor=t.actor,this.key=t.key,this.cache={},this.bus=t.bus,this.sendPres=function(t,e,r){void 0===r&&(r=!1);var n={},o=!0;return function(){var e=arguments,s=this,i=r&&o,c=function(){t.apply(s,e),n[e[0]]=null};i&&(o=!1,c()),n[arguments[0]]||(n[arguments[0]]=setTimeout(c,40))}}((function(t,r){e.ws.send("presence:cmd",r)})),this.bootstrap(t.checkpoint)}var e=t.prototype;return e.bootstrap=function(t){this.cache=i({},this.cache,t.presence[this.key]||{})},e.getAll=function(){return this.withoutExpired()},e.getMine=function(){var t;return null===(t=(this.cache||{})[this.actor])||void 0===t?void 0:t.value},e.withoutExpired=function(){var t={};for(var e in this.cache){var r=this.cache[e];new Date>r.expAt?delete this.cache[e]:t[e]=r.value}return t},e.withoutActorOrExpired=function(t){var e={};for(var r in this.cache)for(var n in this.cache[r]){var o=this.cache[n];o&&(n===t&&this.cache[n]||new Date>o.expAt?delete this.cache[n]:e[n]=o.value)}return e},e.set=function(t,e){var r=e||60,n=Math.round((new Date).getTime()/1e3)+r;this.sendPres(this.key,{room:this.roomID,key:this.key,value:JSON.stringify(t),expAt:n}),this.cache[this.actor]={value:t,expAt:new Date(1e3*n)};var o=this.withoutExpired();return this.bus.publish({key:this.key,valuesByUser:o}),o},e.dangerouslyUpdateClientDirectly=function(t,e){if("room:rm_guest"===t)return this.withoutActorOrExpired(e.guest);if("presence:expire"===t)return this.withoutExpired();if(e.room!==this.roomID)return!1;if(e.from===this.actor)return!1;var r={expAt:new Date(1e3*e.expAt),value:JSON.parse(e.value)};return this.cache[e.from]=r,this.withoutExpired()},t}(),w=function(){function t(){this.isPublishing=!1,this.subs=new Set}var e=t.prototype;return e.unsubscribe=function(t){this.subs.delete(t)},e.subscribe=function(t){return this.subs.add(t),t},e.publish=function(t){if(this.isPublishing)throw new Error("Infinite loop detected, see more: See more: https://err.sh/getroomservice/browser/infinite-loop");this.isPublishing=!0,this.subs.forEach((function(e){e(t)})),this.isPublishing=!1},t}(),k=["mcreate","mput","mputref","mdel"],j=["lcreate","lins","linsref","lput","lputref","ldel"],S=function(){function t(t){this.presenceClients={},this.listClients={},this.mapClients={},this.expires={},this.queueIncomingCmds=!0,this.cmdQueue=[],this.mapCallbacksByObjID={},this.listCallbacksByObjID={},this.presenceCallbacksByKey={},this.ws=new C({dispatcher:this,wsURL:t.wsURL,docsURL:t.docsURL,room:t.roomID,session:t.session}),this.roomID=t.roomID,this.docID=t.bootstrapState.document.id,this.actor=t.actor,this.bootstrapState=t.bootstrapState}var n=t.prototype;return n.forwardCmd=function(t,e){this.queueIncomingCmds?this.cmdQueue.push([t,e]):this.processCmd(t,e)},n.processCmd=function(t,e){"doc:fwd"==t&&"args"in e&&this.dispatchDocCmd(e),"presence:fwd"==t&&"expAt"in e&&this.dispatchPresenceCmd(e),"room:rm_guest"==t&&"guest"in e&&this.dispatchRmGuest(e)},n.bootstrap=function(t){this.bootstrapState=t;for(var e=0,r=Object.entries(this.listClients);e<r.length;e++)r[e][1].bootstrap(t);for(var n=0,o=Object.entries(this.mapClients);n<o.length;n++)o[n][1].bootstrap(t);for(var s=0,i=Object.entries(this.presenceClients);s<i.length;s++)i[s][1].bootstrap(t);this.queueIncomingCmds=!1;for(var c,u=a(this.cmdQueue);!(c=u()).done;){var h=c.value;this.processCmd(h[0],h[1])}this.cmdQueue.length=0},n.startQueueingCmds=function(){this.queueIncomingCmds=!0},n.dispatchDocCmd=function(t){if(t.room===this.roomID)if(!t.args||t.args.length<3)console.error("Unexpected command: ",t.args);else if(!r.vsReader(atob).isOlderVS(t.vs,this.bootstrapState.document.vs)&&t.from!==this.actor){var e=[t.args[0],t.args[1],t.args[2]],n=e[0],o=e[2];e[1]===this.docID&&(k.includes(n)?this.dispatchMapCmd(o,t):j.includes(n)?this.dispatchListCmd(o,t):console.warn("Unhandled Room Service doc:fwd command: "+n+". Consider updating the Room Service client."))}},n.dispatchRmGuest=function(t){if(t.room===this.roomID)for(var e=0,r=Object.entries(this.presenceClients);e<r.length;e++)for(var n,o=r[e],s=o[0],i=o[1].dangerouslyUpdateClientDirectly("room:rm_guest",t),c=a(this.presenceCallbacksByKey[s]||[]);!(n=c()).done;)(0,n.value)(i,t.guest)},n.dispatchMapCmd=function(t,e){this.mapClients[t]||this.createMapLocally(t);for(var r,n=this.mapClients[t].dangerouslyUpdateClientDirectly(e.args),o=a(this.mapCallbacksByObjID[t]||[]);!(r=o()).done;)(0,r.value)(n.toObject(),e.from)},n.dispatchListCmd=function(t,e){this.listClients[t]||this.createListLocally(t);for(var r,n=this.listClients[t].dangerouslyUpdateClientDirectly(e.args),o=a(this.listCallbacksByObjID[t]||[]);!(r=o()).done;)(0,r.value)(n.toArray(),e.from)},n.dispatchPresenceCmd=function(t){var e=this;if(t.room===this.roomID&&t.from!==this.actor){var r=t.key,n=this.presence(r),o=(new Date).getTime()/1e3,s=t.expAt-o;if(!(s<0)){if(s<43200){this.expires[r]&&clearTimeout(this.expires[r]);var i=setTimeout((function(){var o=n.dangerouslyUpdateClientDirectly("presence:expire",{key:t.key});if(o)for(var s,i=a(null!==(c=e.presenceCallbacksByKey[r])&&void 0!==c?c:[]);!(s=i()).done;){var c;(0,s.value)(o,t.from)}}),1e3*s);this.expires[r]=i}var c=n.dangerouslyUpdateClientDirectly("presence:fwd",t);if(c)for(var u,h=a(null!==(l=this.presenceCallbacksByKey[r])&&void 0!==l?l:[]);!(u=h()).done;){var l;(0,u.value)(c,t.from)}}}},n.createListLocally=function(t){var e=this,r=new w;r.subscribe((function(r){for(var n,o=e.listClients[t],s=a(e.listCallbacksByObjID[t]||[]);!(n=s()).done;)(0,n.value)(o.toArray(),r.from)}));var n=new I({checkpoint:this.bootstrapState.document,roomID:this.roomID,docID:this.docID,listID:t,ws:this.ws,actor:this.actor,bus:r});return this.listClients[t]=n,n},n.list=function(t){return this.listClients[t]?this.listClients[t]:(this.bootstrapState.document.lists[t]||(this.ws.send("doc:cmd",{args:["lcreate",this.docID,t],room:this.roomID}),this.bootstrapState.document.lists[t]={afters:[],ids:[],values:[]}),this.createListLocally(t))},n.createMapLocally=function(t){var e=this,r=new w;r.subscribe((function(r){for(var n,o=e.mapClients[t],s=a(e.mapCallbacksByObjID[t]||[]);!(n=s()).done;)(0,n.value)(o.toObject(),r.from)}));var n=new g({checkpoint:this.bootstrapState.document,roomID:this.roomID,docID:this.docID,mapID:t,ws:this.ws,bus:r,actor:this.actor});return this.mapClients[t]=n,n},n.map=function(t){return this.mapClients[t]?this.mapClients[t]:(this.bootstrapState.document.maps[t]||this.ws.send("doc:cmd",{args:["mcreate",this.docID,t],room:this.roomID}),this.createMapLocally(t))},n.presence=function(t){var e=this;if(this.presenceClients[t])return this.presenceClients[t];var r=new w;r.subscribe((function(t){for(var r,n=a(e.presenceCallbacksByKey[t.key]||[]);!(r=n()).done;)(0,r.value)(t.valuesByUser,e.actor)}));var n=new D({checkpoint:this.bootstrapState,roomID:this.roomID,ws:this.ws,actor:this.actor,key:t,bus:r});try{this.presenceClients[t]=n}catch(t){throw new Error("Don't Freeze State. See more: https://err.sh/getroomservice/browser/dont-freeze")}return this.presenceClients[t]},n.subscribe=function(t,e){if(t instanceof D)return this.subscribePresence(t,e);var r,n=function(t,r){e(t,r)};return t instanceof g&&(this.mapCallbacksByObjID[r=t.id]=this.mapCallbacksByObjID[r]||[],this.mapCallbacksByObjID[r].push(n)),t instanceof I&&(this.listCallbacksByObjID[r=t.id]=this.listCallbacksByObjID[r]||[],this.listCallbacksByObjID[r].push(n)),[{objID:r,fn:n}]},n.subscribePresence=function(t,r){t||e(!1);var n=function(t,e){r&&r(t,e)},o=t.key;return this.presenceCallbacksByKey[o]=this.presenceCallbacksByKey[o]||[],this.presenceCallbacksByKey[o].push(n),[{objID:o,fn:n}]},n.unsubscribe=function(t){for(var e,r=a(t);!(e=r()).done;){var n=e.value;n.objID&&(this.mapCallbacksByObjID[n.objID]=P(this.mapCallbacksByObjID[n.objID],n.fn),this.listCallbacksByObjID[n.objID]=P(this.listCallbacksByObjID[n.objID],n.fn),this.presenceCallbacksByKey[n.objID]=P(this.presenceCallbacksByKey[n.objID],n.fn))}},s(t,[{key:"me",get:function(){return this.actor}}]),t}();function P(t,e){return t?t.filter((function(t){return t!==e})):[]}var O=function(){function t(t){this.roomClients={},this.auth=t.auth,this.ctx=t.ctx||{}}return t.prototype.room=function(t){try{var e=this;return e.roomClients[t]?Promise.resolve(e.roomClients[t]):Promise.resolve(function(t){try{return Promise.resolve(function(t,e,r,n){try{var o=function(e){return s?e:Promise.resolve(fetch(t,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({resources:[{object:"document",reference:n,permission:"read_write",room:r},{object:"room",reference:r,permission:"join"}]})})).then((function(t){if(401===t.status)throw new Error("The Auth Webhook returned unauthorized.");if(200!==t.status)throw new Error("The Auth Webhook returned a status code other than 200.");return Promise.resolve(t.json()).then((function(t){var e=t.resources,r=t.token,n=t.user;if(!e||!r||!n){if("Unauthorized"===t.body)throw new Error("The Auth Webhook unexpectedly return unauthorized. You may be using an invalid API key.");throw new Error("The Auth Webhook has an incorrectly formatted JSON response.")}return{token:r,guestReference:n,docID:e.find((function(t){return"document"===t.object})).id,roomID:e.find((function(t){return"room"===t.object})).id}}))}))},s=!1,i=function(){if("function"==typeof t)return Promise.resolve(t({room:r,ctx:e})).then((function(t){if(!t.user)throw new Error("The auth function must return a 'user' key.");var e=t.resources.find((function(t){return"document"===t.object})).id,r=t.resources.find((function(t){return"room"===t.object})).id;return s=!0,{token:t.token,guestReference:t.user,docID:e,roomID:r}}))}();return Promise.resolve(i&&i.then?i.then(o):o(i))}catch(t){return Promise.reject(t)}}(t.authStrategy,t.authCtx,t.room,t.document)).then((function(e){return Promise.resolve(p({url:t.docsURL,token:e.token,docID:e.docID,roomID:e.roomID})).then((function(r){return new S({actor:e.guestReference,bootstrapState:r,token:e.token,roomID:e.roomID,docID:t.document,auth:t.authStrategy,authCtx:t.authCtx,wsURL:"wss://super.roomservice.dev/ws",docsURL:n,session:e})}))}))}catch(t){return Promise.reject(t)}}({docsURL:n,authStrategy:e.auth,authCtx:e.ctx,room:t,document:"default"})).then((function(r){return e.roomClients[t]=r,r}))}catch(t){return Promise.reject(t)}},t}();exports.RoomClient=S,exports.RoomService=O,exports.default=O;
//# sourceMappingURL=browser.cjs.production.min.js.map

@@ -9,3 +9,2 @@ import invariant from 'tiny-invariant';

var DOCS_URL = 'https://super.roomservice.dev/docs';
var PRESENCE_URL = 'https://super.roomservice.dev/presence';

@@ -261,8 +260,2 @@ function _defineProperties(target, props) {

function delay(ms) {
return new Promise(function (resolve) {
return setTimeout(resolve, ms);
});
}
var fetchSession = function fetchSession(strategy, ctx, room, document) {

@@ -371,3 +364,5 @@ try {

})).then(function (res) {
return Promise.resolve(res.json());
return Promise.resolve(res.json()).then(function (doc) {
return doc.body;
});
});

@@ -378,5 +373,5 @@ } catch (e) {

};
var fetchPresence = function fetchPresence(url, token, roomID, key) {
var fetchPresence = function fetchPresence(url, token, roomID) {
try {
return Promise.resolve(fetch(url + '/' + roomID + '/' + encodeURIComponent(key), {
return Promise.resolve(fetch(url + '/' + roomID, {
headers: {

@@ -388,12 +383,14 @@ Authorization: 'Bearer: ' + token

// Parse JSON values
for (var k in doc) {
if (typeof doc[k].value === 'string') {
var json = void 0;
for (var key in Object.keys(doc)) {
for (var actor in Object.keys(doc[key])) {
if (typeof doc[key][actor].value === 'string') {
var json = void 0;
try {
json = JSON.parse(doc[k].value);
} catch (err) {}
try {
json = JSON.parse(doc[key][actor].value);
} catch (err) {}
if (json) {
doc[k].value = json;
if (json) {
doc[key][actor].value = json;
}
}

@@ -410,3 +407,23 @@ }

};
var fetchBootstrapState = function fetchBootstrapState(props) {
try {
return Promise.resolve(Promise.all([fetchPresence(props.url, props.token, props.roomID), fetchDocument(props.url, props.token, props.docID)])).then(function (_ref) {
var allPresence = _ref[0],
documentCheckpoint = _ref[1];
return {
presence: allPresence,
document: documentCheckpoint
};
});
} catch (e) {
return Promise.reject(e);
}
};
function delay(ms) {
return new Promise(function (resolve) {
return setTimeout(resolve, ms);
});
}
var openWS = function openWS(url) {

@@ -447,3 +464,3 @@ try {

this.wsFactory = params.wsFactory || openWS;
this.documentFetch = params.documentFetch || fetchDocument;
this.bootstrapFetch = params.bootstrapFetch || fetchBootstrapState;
this.wsLoop();

@@ -491,7 +508,10 @@ }

return Promise.resolve(_this2.once('room:joined')).then(function () {
return Promise.resolve(_this2.documentFetch(_this2.docsURL, _this2.session.token, _this2.session.docID)).then(function (_ref) {
var body = _ref.body;
return Promise.resolve(_this2.bootstrapFetch({
docID: _this2.session.docID,
roomID: _this2.session.roomID,
url: _this2.docsURL,
token: _this2.session.token
})).then(function (bootstrapState) {
_this2.dispatcher.bootstrap(bootstrapState);
_this2.dispatcher.bootstrap(body);
return ws;

@@ -727,3 +747,3 @@ });

_proto.bootstrap = function bootstrap(checkpoint) {
ListInterpreter.importFromRawCheckpoint(this.store, checkpoint, this.meta.listID);
ListInterpreter.importFromRawCheckpoint(this.store, checkpoint.document, this.meta.listID);
};

@@ -833,3 +853,3 @@

_proto.bootstrap = function bootstrap(checkpoint) {
MapInterpreter.importFromRawCheckpoint(this.store, checkpoint, this.meta.mapID);
MapInterpreter.importFromRawCheckpoint(this.store, checkpoint.document, this.meta.mapID);
};

@@ -942,3 +962,3 @@

this.actor = props.actor;
this.token = props.token;
this.key = props.key;
this.cache = {};

@@ -952,33 +972,39 @@ this.bus = props.bus;

this.sendPres = throttleByFirstArgument(sendPres, 40);
this.bootstrap(props.checkpoint);
}
var _proto = InnerPresenceClient.prototype;
_proto.bootstrap = function bootstrap(checkpoint) {
this.cache = _extends({}, this.cache, checkpoint.presence[this.key] || {});
}
/**
* Gets all values for an identifier, organized by user id.
* @param key the identifier. Ex: "position"
* Gets all values for the presence key this client was created with,
* organized by user id.
*/
;
_proto.getAll = function getAll() {
// only initialize non-present values so we don't lose actors not present in this checkpoint
return this.withoutExpired();
}
/**
* Gets the current user's value.
*/
;
var _proto = InnerPresenceClient.prototype;
_proto.getMine = function getMine() {
var _this$actor;
_proto.getAll = function getAll(key) {
try {
var _this3 = this;
return Promise.resolve(fetchPresence(PRESENCE_URL, _this3.token, _this3.roomID, key)).then(function (val) {
// only initialize non-present values so we don't lose actors not present in this checkpoint
_this3.cache[key] = _extends({}, val, _this3.cache[key] || {});
return _this3.withoutExpired(key);
});
} catch (e) {
return Promise.reject(e);
}
return (_this$actor = (this.cache || {})[this.actor]) === null || _this$actor === void 0 ? void 0 : _this$actor.value;
};
_proto.withoutExpired = function withoutExpired(key) {
_proto.withoutExpired = function withoutExpired() {
var result = {};
for (var actor in this.cache[key]) {
var obj = this.cache[key][actor];
for (var actor in this.cache) {
var obj = this.cache[actor];
if (new Date() > obj.expAt) {
delete this.cache[key][actor];
delete this.cache[actor];
continue;

@@ -998,7 +1024,7 @@ }

for (var a in this.cache[key]) {
var obj = this.cache[key][a];
var obj = this.cache[a];
if (!obj) continue; // remove this actor
if (a === actor && this.cache[key][a]) {
delete this.cache[key][a];
if (a === actor && this.cache[a]) {
delete this.cache[a];
continue;

@@ -1009,3 +1035,3 @@ } // Remove expired

if (new Date() > obj.expAt) {
delete this.cache[key][a];
delete this.cache[a];
continue;

@@ -1019,33 +1045,27 @@ }

return result;
} // Deprecated
;
}
/**
* @param key
* @param value Any arbitrary object, string, boolean, or number.
* @param exp (Optional) Expiration time in seconds
*/
_proto.set = function set(key, value, exp) {
;
_proto.set = function set(value, exp) {
var addition = exp ? exp : 60; // Convert to unix + add seconds
var expAt = Math.round(new Date().getTime() / 1000) + addition;
this.sendPres(key, {
this.sendPres(this.key, {
room: this.roomID,
key: key,
key: this.key,
value: JSON.stringify(value),
expAt: expAt
});
if (!this.cache[key]) {
this.cache[key] = {};
}
this.cache[key][this.actor] = {
this.cache[this.actor] = {
value: value,
expAt: new Date(expAt * 1000)
};
var result = this.withoutExpired(key);
var result = this.withoutExpired();
this.bus.publish({
key: key,
valuesByActor: result
key: this.key,
valuesByUser: result
});

@@ -1061,3 +1081,3 @@ return result;

if (type === 'presence:expire') {
var foo = this.withoutExpired(body.key);
var foo = this.withoutExpired();
return foo;

@@ -1073,19 +1093,6 @@ }

};
if (!this.cache[body.key]) {
this.cache[body.key] = {};
}
this.cache[body.key][body.from] = obj;
return this.withoutExpired(body.key);
this.cache[body.from] = obj;
return this.withoutExpired();
};
_createClass(InnerPresenceClient, [{
key: "me",
get: function get() {
console.warn('presence.me() is deprecated and will be removed in a future version!');
return this.actor;
}
}]);
return InnerPresenceClient;

@@ -1138,7 +1145,11 @@ }();

return Promise.resolve(fetchSession(params.authStrategy, params.authCtx, params.room, params.document)).then(function (session) {
return Promise.resolve(fetchDocument(params.docsURL, session.token, session.docID)).then(function (_ref2) {
var body = _ref2.body;
return Promise.resolve(fetchBootstrapState({
url: params.docsURL,
token: session.token,
docID: session.docID,
roomID: session.roomID
})).then(function (bootstrapState) {
var roomClient = new RoomClient({
actor: session.guestReference,
checkpoint: body,
bootstrapState: bootstrapState,
token: session.token,

@@ -1164,2 +1175,3 @@ roomID: session.roomID,

function RoomClient(params) {
this.presenceClients = {};
this.listClients = {};

@@ -1183,7 +1195,6 @@ this.mapClients = {};

});
this.token = params.token;
this.roomID = params.roomID;
this.docID = params.checkpoint.id;
this.docID = params.bootstrapState.document.id;
this.actor = params.actor;
this.checkpoint = params.checkpoint;
this.bootstrapState = params.bootstrapState;
} // impl WebsocketDispatch

@@ -1217,4 +1228,4 @@

_proto.bootstrap = function bootstrap(checkpoint) {
this.checkpoint = checkpoint;
_proto.bootstrap = function bootstrap(state) {
this.bootstrapState = state;

@@ -1224,3 +1235,3 @@ for (var _i = 0, _Object$entries = Object.entries(this.listClients); _i < _Object$entries.length; _i++) {

client = _Object$entries$_i[1];
client.bootstrap(checkpoint);
client.bootstrap(state);
}

@@ -1232,5 +1243,12 @@

_client.bootstrap(checkpoint);
_client.bootstrap(state);
}
for (var _i3 = 0, _Object$entries3 = Object.entries(this.presenceClients); _i3 < _Object$entries3.length; _i3++) {
var _Object$entries3$_i = _Object$entries3[_i3],
_client2 = _Object$entries3$_i[1];
_client2.bootstrap(state);
}
this.queueIncomingCmds = false;

@@ -1263,3 +1281,3 @@

if (vsReader(atob).isOlderVS(body.vs, this.checkpoint.vs)) {
if (vsReader(atob).isOlderVS(body.vs, this.bootstrapState.document.vs)) {
return;

@@ -1290,10 +1308,10 @@ } // Ignore validated commands

if (body.room !== this.roomID) return;
var client = this.presence();
var newClient = client.dangerouslyUpdateClientDirectly('room:rm_guest', body);
for (var _i3 = 0, _Object$entries3 = Object.entries(this.presenceCallbacksByKey); _i3 < _Object$entries3.length; _i3++) {
var _Object$entries3$_i = _Object$entries3[_i3],
cbs = _Object$entries3$_i[1];
for (var _i4 = 0, _Object$entries4 = Object.entries(this.presenceClients); _i4 < _Object$entries4.length; _i4++) {
var _Object$entries4$_i = _Object$entries4[_i4],
key = _Object$entries4$_i[0],
presenceClient = _Object$entries4$_i[1];
var newClient = presenceClient.dangerouslyUpdateClientDirectly('room:rm_guest', body);
for (var _iterator2 = _createForOfIteratorHelperLoose(cbs), _step2; !(_step2 = _iterator2()).done;) {
for (var _iterator2 = _createForOfIteratorHelperLoose(this.presenceCallbacksByKey[key] || []), _step2; !(_step2 = _iterator2()).done;) {
var cb = _step2.value;

@@ -1338,4 +1356,4 @@ cb(newClient, body.guest);

if (body.from === this.actor) return;
var client = this.presence();
var key = body.key;
var client = this.presence(key);
var now = new Date().getTime() / 1000;

@@ -1395,3 +1413,3 @@ var secondsTillTimeout = body.expAt - now;

var l = new InnerListClient({
checkpoint: this.checkpoint,
checkpoint: this.bootstrapState.document,
roomID: this.roomID,

@@ -1414,3 +1432,3 @@ docID: this.docID,

if (!this.checkpoint.lists[name]) {
if (!this.bootstrapState.document.lists[name]) {
this.ws.send('doc:cmd', {

@@ -1421,3 +1439,3 @@ args: ['lcreate', this.docID, name],

this.checkpoint.lists[name] = {
this.bootstrapState.document.lists[name] = {
afters: [],

@@ -1445,3 +1463,3 @@ ids: [],

var m = new InnerMapClient({
checkpoint: this.checkpoint,
checkpoint: this.bootstrapState.document,
roomID: this.roomID,

@@ -1464,3 +1482,3 @@ docID: this.docID,

if (!this.checkpoint.maps[name]) {
if (!this.bootstrapState.document.maps[name]) {
this.ws.send('doc:cmd', {

@@ -1475,7 +1493,7 @@ args: ['mcreate', this.docID, name],

_proto.presence = function presence() {
_proto.presence = function presence(key) {
var _this4 = this;
if (this.InnerPresenceClient) {
return this.InnerPresenceClient;
if (this.presenceClients[key]) {
return this.presenceClients[key];
}

@@ -1487,10 +1505,11 @@

var cb = _step9.value;
cb(body.valuesByActor, _this4.actor);
cb(body.valuesByUser, _this4.actor);
}
});
var p = new InnerPresenceClient({
checkpoint: this.bootstrapState,
roomID: this.roomID,
ws: this.ws,
actor: this.actor,
token: this.token,
key: key,
bus: bus

@@ -1500,3 +1519,3 @@ });

try {
this.InnerPresenceClient = p;
this.presenceClients[key] = p;
} catch (err) {

@@ -1506,9 +1525,9 @@ throw new Error("Don't Freeze State. See more: https://err.sh/getroomservice/browser/dont-freeze");

return this.InnerPresenceClient;
return this.presenceClients[key];
};
_proto.subscribe = function subscribe(obj, onChangeFnOrString, onChangeFn) {
_proto.subscribe = function subscribe(obj, onChangeFn) {
// Presence handler
if (typeof onChangeFnOrString === 'string') {
return this.subscribePresence(obj, onChangeFnOrString, onChangeFn);
if (obj instanceof InnerPresenceClient) {
return this.subscribePresence(obj, onChangeFn);
} // create new closure so fns can be subscribed/unsubscribed multiple times

@@ -1518,3 +1537,3 @@

var cb = function cb(obj, from) {
onChangeFnOrString(obj, from);
onChangeFn(obj, from);
};

@@ -1532,4 +1551,4 @@

if (obj instanceof InnerListClient) {
var _client2 = obj;
objID = _client2.id;
var _client3 = obj;
objID = _client3.id;
this.listCallbacksByObjID[objID] = this.listCallbacksByObjID[objID] || [];

@@ -1545,3 +1564,3 @@ this.listCallbacksByObjID[objID].push(cb);

_proto.subscribePresence = function subscribePresence(obj, key, onChangeFn) {
_proto.subscribePresence = function subscribePresence(obj, onChangeFn) {
!obj ? process.env.NODE_ENV !== "production" ? invariant(false, 'subscribe() expects the first argument to not be undefined.') : invariant(false) : void 0; // create new closure so fns can be subscribed/unsubscribed multiple times

@@ -1555,2 +1574,3 @@

var key = obj.key;
this.presenceCallbacksByKey[key] = this.presenceCallbacksByKey[key] || [];

@@ -1557,0 +1577,0 @@ this.presenceCallbacksByKey[key].push(cb);

import { SuperlumeSend } from './ws';
import { ObjectClient, DocumentCheckpoint } from './types';
import { LocalBus } from './localbus';
import { BootstrapState } from 'remote';
export declare type ListObject = Array<any>;

@@ -25,3 +26,3 @@ export declare class InnerListClient<T extends ListObject> implements ObjectClient {

});
bootstrap(checkpoint: DocumentCheckpoint): void;
bootstrap(checkpoint: BootstrapState): void;
private sendCmd;

@@ -28,0 +29,0 @@ private clone;

@@ -5,2 +5,3 @@ import { ObjectClient } from './types';

import { DocumentCheckpoint } from '@roomservice/core';
import { BootstrapState } from 'remote';
export declare type MapObject = {

@@ -28,3 +29,3 @@ [key: string]: any;

});
bootstrap(checkpoint: DocumentCheckpoint): void;
bootstrap(checkpoint: BootstrapState): void;
get id(): string;

@@ -31,0 +32,0 @@ private sendCmd;

@@ -5,39 +5,45 @@ import { SuperlumeSend } from './ws';

import { LocalBus } from 'localbus';
import { BootstrapState } from 'remote';
export declare type LocalPresenceUpdate = {
key: string;
valuesByActor: {
valuesByUser: {
[key: string]: any;
};
};
export declare class InnerPresenceClient {
declare type ValuesByUser<T extends any> = {
[key: string]: T;
};
export declare class InnerPresenceClient<T extends any> {
private roomID;
private ws;
private actor;
private token;
private cache;
private sendPres;
private bus;
key: string;
constructor(props: {
roomID: string;
checkpoint: BootstrapState;
ws: SuperlumeSend;
actor: string;
token: string;
key: string;
bus: LocalBus<LocalPresenceUpdate>;
});
bootstrap(checkpoint: BootstrapState): void;
/**
* Gets all values for an identifier, organized by user id.
* @param key the identifier. Ex: "position"
* Gets all values for the presence key this client was created with,
* organized by user id.
*/
getAll<T extends any>(key: string): Promise<{
[key: string]: T;
}>;
getAll(): ValuesByUser<T>;
/**
* Gets the current user's value.
*/
getMine(): T | undefined;
private withoutExpired;
private withoutActorOrExpired;
get me(): string;
/**
* @param key
* @param value Any arbitrary object, string, boolean, or number.
* @param exp (Optional) Expiration time in seconds
*/
set<T extends any>(key: string, value: T, exp?: number): {
set(value: T, exp?: number): {
[key: string]: T;

@@ -57,1 +63,2 @@ };

}
export {};

@@ -1,4 +0,17 @@

import { Message, DocumentCheckpoint, PresenceCheckpoint, AuthStrategy } from './types';
export declare function fetchPresence<T extends any>(url: string, token: string, roomID: string, key: string): Promise<PresenceCheckpoint<T>>;
export declare function fetchDocument(url: string, token: string, docID: string): Promise<Message<DocumentCheckpoint>>;
import { DocumentCheckpoint, PresenceCheckpoint, AuthStrategy } from './types';
declare type AllPresence = {
[key: string]: PresenceCheckpoint<any>;
};
export interface BootstrapState {
presence: AllPresence;
document: DocumentCheckpoint;
}
export declare function fetchBootstrapState(props: {
url: string;
token: string;
roomID: string;
docID: string;
}): Promise<BootstrapState>;
export declare function fetchPresence(url: string, token: string, roomID: string): Promise<AllPresence>;
export declare function fetchDocument(url: string, token: string, docID: string): Promise<DocumentCheckpoint>;
export interface ServerSession {

@@ -19,1 +32,2 @@ token: string;

export declare function fetchSession<T extends object>(strategy: AuthStrategy<T>, ctx: T, room: string, document: string): Promise<LocalSession>;
export {};
import { ForwardedMessageBody, WebsocketDispatch } from './ws';
import { DocumentCheckpoint, AuthStrategy, Prop } from './types';
import { LocalSession } from './remote';
import { AuthStrategy, Prop } from './types';
import { LocalSession, BootstrapState } from './remote';
import { InnerListClient, ListObject } from './ListClient';

@@ -18,10 +18,9 @@ import { InnerMapClient, MapObject } from './MapClient';

export declare type ListClient<T extends ListObject> = Omit<InnerListClient<T>, 'dangerouslyUpdateClientDirectly' | 'id'>;
export declare type PresenceClient = Omit<InnerPresenceClient, 'dangerouslyUpdateClientDirectly'>;
export declare type PresenceClient<T extends any> = Omit<InnerPresenceClient<T>, 'dangerouslyUpdateClientDirectly'>;
export declare class RoomClient implements WebsocketDispatch {
private token;
private roomID;
private docID;
private actor;
private checkpoint;
private InnerPresenceClient?;
private bootstrapState;
private presenceClients;
private listClients;

@@ -38,3 +37,3 @@ private mapClients;

actor: string;
checkpoint: DocumentCheckpoint;
bootstrapState: BootstrapState;
token: string;

@@ -46,3 +45,3 @@ roomID: string;

processCmd(msgType: string, body: ForwardedMessageBody): void;
bootstrap(checkpoint: DocumentCheckpoint): void;
bootstrap(state: BootstrapState): void;
private queueIncomingCmds;

@@ -61,3 +60,3 @@ private cmdQueue;

map<T extends MapObject>(name: string): MapClient<T>;
presence(): PresenceClient;
presence<T extends any>(key: string): PresenceClient<T>;
private mapCallbacksByObjID;

@@ -70,3 +69,3 @@ private listCallbacksByObjID;

subscribe<T extends MapObject>(map: MapClient<T>, onChangeFn: (map: T, from: string) => any): ListenerBundle;
subscribe<T extends any>(presence: PresenceClient, key: string, onChangeFn: (obj: {
subscribe<T extends any>(presence: PresenceClient<T>, onChangeFn: (obj: {
[key: string]: T;

@@ -73,0 +72,0 @@ }, from: string) => any): ListenerBundle;

import { DocumentCheckpoint } from './types';
import { LocalSession } from 'remote';
import { BootstrapState, LocalSession } from 'remote';
export declare function mockSession(): LocalSession;
export declare function mockCheckpoint(): DocumentCheckpoint;
export declare function mockBootstrapState(): BootstrapState;

@@ -1,2 +0,2 @@

import ReverseTree from './ReverseTree';
import { ReverseTree } from '@roomservice/core/dist/ReverseTree';
export interface Ref {

@@ -3,0 +3,0 @@ type: 'map' | 'list';

import { WebSocketDocFwdMessage, WebSocketClientMessage, WebSocketDocCmdMessage, WebSocketPresenceCmdMessage, WebSocketPresenceFwdMessage, WebSocketLeaveMessage, WebSocketJoinMessage } from './wsMessages';
import { Prop, DocumentCheckpoint, Message } from 'types';
import { LocalSession } from './remote';
import { Prop } from 'types';
import { BootstrapState, LocalSession } from './remote';
export declare class ReconnectingWebSocket implements SuperlumeSend {

@@ -10,3 +10,3 @@ private wsURL;

private wsFactory;
private documentFetch;
private bootstrapFetch;
private currentConn?;

@@ -23,3 +23,3 @@ private pendingConn?;

wsFactory?: WebSocketFactory;
documentFetch?: DocumentFetch;
bootstrapFetch?: BootstrapFetch;
});

@@ -50,3 +50,3 @@ close(): void;

forwardCmd(type: string, body: ForwardedMessageBody): void;
bootstrap(checkpoint: DocumentCheckpoint): void;
bootstrap(state: BootstrapState): void;
startQueueingCmds(): void;

@@ -61,2 +61,7 @@ }

export declare type WebSocketTransport = Pick<WebSocket, 'send' | 'onclose' | 'onmessage' | 'onerror' | 'close'>;
export declare type DocumentFetch = (url: string, token: string, docID: string) => Promise<Message<DocumentCheckpoint>>;
export declare type BootstrapFetch = (props: {
url: string;
token: string;
roomID: string;
docID: string;
}) => Promise<BootstrapState>;
{
"version": "3.0.0-6",
"version": "3.0.0-7",
"license": "MIT",

@@ -4,0 +4,0 @@ "main": "dist/index.js",

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc