diff options
Diffstat (limited to 'web/react/stores')
-rw-r--r-- | web/react/stores/browser_store.jsx | 48 | ||||
-rw-r--r-- | web/react/stores/post_store.jsx | 107 | ||||
-rw-r--r-- | web/react/stores/socket_store.jsx | 128 | ||||
-rw-r--r-- | web/react/stores/team_store.jsx | 143 | ||||
-rw-r--r-- | web/react/stores/user_store.jsx | 14 |
5 files changed, 291 insertions, 149 deletions
diff --git a/web/react/stores/browser_store.jsx b/web/react/stores/browser_store.jsx index 4eed754cc..436b8d76d 100644 --- a/web/react/stores/browser_store.jsx +++ b/web/react/stores/browser_store.jsx @@ -3,7 +3,9 @@ var UserStore; function getPrefix() { - if (!UserStore) UserStore = require('./user_store.jsx'); + if (!UserStore) { + UserStore = require('./user_store.jsx'); + } return UserStore.getCurrentId() + '_'; } @@ -11,15 +13,15 @@ function getPrefix() { var BROWSER_STORE_VERSION = '.4'; module.exports = { - _initialized: false, + initialized: false, - _initialize: function() { - var currentVersion = localStorage.getItem("local_storage_version"); + initialize: function() { + var currentVersion = localStorage.getItem('local_storage_version'); if (currentVersion !== BROWSER_STORE_VERSION) { this.clear(); - localStorage.setItem("local_storage_version", BROWSER_STORE_VERSION); + localStorage.setItem('local_storage_version', BROWSER_STORE_VERSION); } - this._initialized = true; + this.initialized = true; }, getItem: function(name, defaultValue) { @@ -31,19 +33,25 @@ module.exports = { }, removeItem: function(name) { - if (!this._initialized) this._initialize(); + if (!this.initialized) { + this.initialize(); + } localStorage.removeItem(getPrefix() + name); }, setGlobalItem: function(name, value) { - if (!this._initialized) this._initialize(); + if (!this.initialized) { + this.initialize(); + } localStorage.setItem(name, JSON.stringify(value)); }, getGlobalItem: function(name, defaultValue) { - if (!this._initialized) this._initialize(); + if (!this.initialized) { + this.initialize(); + } var result = null; try { @@ -58,7 +66,9 @@ module.exports = { }, removeGlobalItem: function(name) { - if (!this._initialized) this._initialize(); + if (!this.initialized) { + this.initialize(); + } localStorage.removeItem(name); }, @@ -70,10 +80,12 @@ module.exports = { /** * Preforms the given action on each item that has the given prefix - * Signiture for action is action(key, value) + * Signature for action is action(key, value) */ - actionOnItemsWithPrefix: function (prefix, action) { - if (!this._initialized) this._initialize(); + actionOnItemsWithPrefix: function(prefix, action) { + if (!this.initialized) { + this.initialize(); + } var globalPrefix = getPrefix(); var globalPrefixiLen = globalPrefix.length; @@ -87,14 +99,14 @@ module.exports = { isLocalStorageSupported: function() { try { - sessionStorage.setItem("testSession", '1'); - sessionStorage.removeItem("testSession"); + sessionStorage.setItem('testSession', '1'); + sessionStorage.removeItem('testSession'); - localStorage.setItem("testLocal", '1'); - if (localStorage.getItem("testLocal") != '1') { + localStorage.setItem('testLocal', '1'); + if (localStorage.getItem('testLocal') !== '1') { return false; } - localStorage.removeItem("testLocal", '1'); + localStorage.removeItem('testLocal', '1'); return true; } catch (e) { diff --git a/web/react/stores/post_store.jsx b/web/react/stores/post_store.jsx index 9ebdf734c..3e4fde30a 100644 --- a/web/react/stores/post_store.jsx +++ b/web/react/stores/post_store.jsx @@ -19,7 +19,6 @@ var MENTION_DATA_CHANGE_EVENT = 'mention_data_change'; var ADD_MENTION_EVENT = 'add_mention'; var PostStore = assign({}, EventEmitter.prototype, { - emitChange: function emitChange() { this.emit(CHANGE_EVENT); }, @@ -110,6 +109,108 @@ var PostStore = assign({}, EventEmitter.prototype, { getPosts: function getPosts(channelId) { return BrowserStore.getItem('posts_' + channelId); }, + storePost: function(post) { + this.pStorePost(post); + this.emitChange(); + }, + pStorePost: function(post) { + var postList = PostStore.getPosts(post.channel_id); + if (!postList) { + return; + } + + if (post.pending_post_id !== '') { + this.removePendingPost(post.channel_id, post.pending_post_id); + } + + post.pending_post_id = ''; + + postList.posts[post.id] = post; + if (postList.order.indexOf(post.id) === -1) { + postList.order.unshift(post.id); + } + + this.pStorePosts(post.channel_id, postList); + }, + storePendingPost: function(post) { + post.state = Constants.POST_LOADING; + + var postList = this.getPendingPosts(post.channel_id); + if (!postList) { + postList = {posts: {}, order: []}; + } + + postList.posts[post.pending_post_id] = post; + postList.order.unshift(post.pending_post_id); + this._storePendingPosts(post.channel_id, postList); + this.emitChange(); + }, + _storePendingPosts: function(channelId, postList) { + var posts = postList.posts; + + // sort failed posts to the bottom + postList.order.sort(function postSort(a, b) { + if (posts[a].state === Constants.POST_LOADING && posts[b].state === Constants.POST_FAILED) { + return 1; + } + if (posts[a].state === Constants.POST_FAILED && posts[b].state === Constants.POST_LOADING) { + return -1; + } + + if (posts[a].create_at > posts[b].create_at) { + return -1; + } + if (posts[a].create_at < posts[b].create_at) { + return 1; + } + + return 0; + }); + + BrowserStore.setItem('pending_posts_' + channelId, postList); + }, + getPendingPosts: function(channelId) { + return BrowserStore.getItem('pending_posts_' + channelId); + }, + removePendingPost: function(channelId, pendingPostId) { + this._removePendingPost(channelId, pendingPostId); + this.emitChange(); + }, + _removePendingPost: function(channelId, pendingPostId) { + var postList = this.getPendingPosts(channelId); + if (!postList) { + return; + } + + if (pendingPostId in postList.posts) { + delete postList.posts[pendingPostId]; + } + var index = postList.order.indexOf(pendingPostId); + if (index >= 0) { + postList.order.splice(index, 1); + } + + this._storePendingPosts(channelId, postList); + }, + clearPendingPosts: function() { + BrowserStore.actionOnItemsWithPrefix('pending_posts_', function clearPending(key) { + BrowserStore.removeItem(key); + }); + }, + updatePendingPost: function(post) { + var postList = this.getPendingPosts(post.channel_id); + if (!postList) { + postList = {posts: {}, order: []}; + } + + if (postList.order.indexOf(post.pending_post_id) === -1) { + return; + } + + postList.posts[post.pending_post_id] = post; + this._storePendingPosts(post.channel_id, postList); + this.emitChange(); + }, storeSearchResults: function storeSearchResults(results, isMentionSearch) { BrowserStore.setItem('search_results', results); BrowserStore.setItem('is_mention_search', Boolean(isMentionSearch)); @@ -181,6 +282,10 @@ PostStore.dispatchToken = AppDispatcher.register(function registry(payload) { PostStore.pStorePosts(action.id, action.post_list); PostStore.emitChange(); break; + case ActionTypes.RECIEVED_POST: + PostStore.pStorePost(action.post); + PostStore.emitChange(); + break; case ActionTypes.RECIEVED_SEARCH: PostStore.storeSearchResults(action.results, action.is_mention_search); PostStore.emitSearchChange(); diff --git a/web/react/stores/socket_store.jsx b/web/react/stores/socket_store.jsx index 8ebb854c9..c3c331828 100644 --- a/web/react/stores/socket_store.jsx +++ b/web/react/stores/socket_store.jsx @@ -15,72 +15,80 @@ var CHANGE_EVENT = 'change'; var conn; var SocketStore = assign({}, EventEmitter.prototype, { - initialize: function(self) { - if (!UserStore.getCurrentId()) return; - - if (!self) self = this; - self.setMaxListeners(0); - - if (window["WebSocket"] && !conn) { - var protocol = window.location.protocol == "https:" ? "wss://" : "ws://"; - var port = window.location.protocol == "https:" ? ":8443" : ""; - var conn_url = protocol + location.host + port + "/api/v1/websocket"; - console.log("connecting to " + conn_url); - conn = new WebSocket(conn_url); - - conn.onclose = function(evt) { - console.log("websocket closed"); - console.log(evt); - conn = null; - setTimeout(function(){self.initialize(self)}, 3000); - }; - - conn.onerror = function(evt) { - console.log("websocket error"); - console.log(evt); - }; - - conn.onmessage = function(evt) { - AppDispatcher.handleServerAction({ - type: ActionTypes.RECIEVED_MSG, - msg: JSON.parse(evt.data) - }); - }; - } - }, - emitChange: function(msg) { - this.emit(CHANGE_EVENT, msg); - }, - addChangeListener: function(callback) { - this.on(CHANGE_EVENT, callback); - }, - removeChangeListener: function(callback) { - this.removeListener(CHANGE_EVENT, callback); - }, - sendMessage: function (msg) { - if (conn && conn.readyState === WebSocket.OPEN) { - conn.send(JSON.stringify(msg)); - } else if (!conn || conn.readyState === WebSocket.Closed) { - conn = null; - this.initialize(); + initialize: function() { + if (!UserStore.getCurrentId()) { + return; + } + + var self = this; + self.setMaxListeners(0); + + if (window.WebSocket && !conn) { + var protocol = 'ws://'; + var port = ''; + if (window.location.protocol === 'https:') { + protocol = 'wss://'; + port = ':8443'; + } + var connUrl = protocol + location.host + port + '/api/v1/websocket'; + console.log('connecting to ' + connUrl); + conn = new WebSocket(connUrl); + + conn.onclose = function closeConn(evt) { + console.log('websocket closed'); + console.log(evt); + conn = null; + setTimeout( + function reconnect() { + self.initialize(); + }, + 3000 + ); + }; + + conn.onerror = function connError(evt) { + console.log('websocket error'); + console.log(evt); + }; + + conn.onmessage = function connMessage(evt) { + AppDispatcher.handleServerAction({ + type: ActionTypes.RECIEVED_MSG, + msg: JSON.parse(evt.data) + }); + }; + } + }, + emitChange: function(msg) { + this.emit(CHANGE_EVENT, msg); + }, + addChangeListener: function(callback) { + this.on(CHANGE_EVENT, callback); + }, + removeChangeListener: function(callback) { + this.removeListener(CHANGE_EVENT, callback); + }, + sendMessage: function(msg) { + if (conn && conn.readyState === WebSocket.OPEN) { + conn.send(JSON.stringify(msg)); + } else if (!conn || conn.readyState === WebSocket.Closed) { + conn = null; + this.initialize(); + } } - } }); SocketStore.dispatchToken = AppDispatcher.register(function(payload) { - var action = payload.action; + var action = payload.action; - switch(action.type) { - case ActionTypes.RECIEVED_MSG: - SocketStore.emitChange(action.msg); - break; - default: - } + switch (action.type) { + case ActionTypes.RECIEVED_MSG: + SocketStore.emitChange(action.msg); + break; + + default: + } }); SocketStore.initialize(); module.exports = SocketStore; - - - - diff --git a/web/react/stores/team_store.jsx b/web/react/stores/team_store.jsx index e6380d19e..3f2248c44 100644 --- a/web/react/stores/team_store.jsx +++ b/web/react/stores/team_store.jsx @@ -13,89 +13,94 @@ var CHANGE_EVENT = 'change'; var utils; function getWindowLocationOrigin() { - if (!utils) utils = require('../utils/utils.jsx'); + if (!utils) { + utils = require('../utils/utils.jsx'); + } return utils.getWindowLocationOrigin(); } var TeamStore = assign({}, EventEmitter.prototype, { - emitChange: function() { - this.emit(CHANGE_EVENT); - }, - addChangeListener: function(callback) { - this.on(CHANGE_EVENT, callback); - }, - removeChangeListener: function(callback) { - this.removeListener(CHANGE_EVENT, callback); - }, - get: function(id) { - var c = this._getTeams(); - return c[id]; - }, - getByName: function(name) { - var current = null; - var t = this._getTeams(); + emitChange: function() { + this.emit(CHANGE_EVENT); + }, + addChangeListener: function(callback) { + this.on(CHANGE_EVENT, callback); + }, + removeChangeListener: function(callback) { + this.removeListener(CHANGE_EVENT, callback); + }, + get: function(id) { + var c = this.pGetTeams(); + return c[id]; + }, + getByName: function(name) { + var t = this.pGetTeams(); - for (id in t) { - if (t[id].name == name) { - return t[id]; + for (var id in t) { + if (t[id].name === name) { + return t[id]; + } } - } - return null; - }, - getAll: function() { - return this._getTeams(); - }, - setCurrentId: function(id) { - if (id == null) - BrowserStore.removeItem("current_team_id"); - else - BrowserStore.setItem("current_team_id", id); - }, - getCurrentId: function() { - return BrowserStore.getItem("current_team_id"); - }, - getCurrent: function() { - var currentId = TeamStore.getCurrentId(); + return null; + }, + getAll: function() { + return this.pGetTeams(); + }, + setCurrentId: function(id) { + if (id === null) { + BrowserStore.removeItem('current_team_id'); + } else { + BrowserStore.setItem('current_team_id', id); + } + }, + getCurrentId: function() { + return BrowserStore.getItem('current_team_id'); + }, + getCurrent: function() { + var currentId = TeamStore.getCurrentId(); - if (currentId != null) - return this.get(currentId); - else - return null; - }, - getCurrentTeamUrl: function() { - return getWindowLocationOrigin() + "/" + this.getCurrent().name; - }, - storeTeam: function(team) { - var teams = this._getTeams(); - teams[team.id] = team; - this._storeTeams(teams); - }, - _storeTeams: function(teams) { - BrowserStore.setItem("user_teams", teams); - }, - _getTeams: function() { - return BrowserStore.getItem("user_teams", {}); - } + if (currentId !== null) { + return this.get(currentId); + } + return null; + }, + getCurrentTeamUrl: function() { + if (this.getCurrent()) { + return getWindowLocationOrigin() + '/' + this.getCurrent().name; + } + return null; + }, + storeTeam: function(team) { + var teams = this.pGetTeams(); + teams[team.id] = team; + this.pStoreTeams(teams); + }, + pStoreTeams: function(teams) { + BrowserStore.setItem('user_teams', teams); + }, + pGetTeams: function() { + return BrowserStore.getItem('user_teams', {}); + } }); -TeamStore.dispatchToken = AppDispatcher.register(function(payload) { - var action = payload.action; +TeamStore.dispatchToken = AppDispatcher.register(function registry(payload) { + var action = payload.action; - switch(action.type) { + switch (action.type) { - case ActionTypes.CLICK_TEAM: - TeamStore.setCurrentId(action.id); - TeamStore.emitChange(); - break; + case ActionTypes.CLICK_TEAM: + TeamStore.setCurrentId(action.id); + TeamStore.emitChange(); + break; - case ActionTypes.RECIEVED_TEAM: - TeamStore.storeTeam(action.team); - TeamStore.emitChange(); - break; + case ActionTypes.RECIEVED_TEAM: + TeamStore.storeTeam(action.team); + TeamStore.emitChange(); + break; - default: - } + default: + } }); module.exports = TeamStore; diff --git a/web/react/stores/user_store.jsx b/web/react/stores/user_store.jsx index f8616c6ab..248495dac 100644 --- a/web/react/stores/user_store.jsx +++ b/web/react/stores/user_store.jsx @@ -4,6 +4,7 @@ var AppDispatcher = require('../dispatcher/app_dispatcher.jsx'); var EventEmitter = require('events').EventEmitter; var assign = require('object-assign'); +var client = require('../utils/client.jsx'); var Constants = require('../utils/constants.jsx'); var ActionTypes = Constants.ActionTypes; @@ -72,7 +73,7 @@ var UserStore = assign({}, EventEmitter.prototype, { BrowserStore.setGlobalItem('current_user_id', id); } }, - getCurrentId: function() { + getCurrentId: function(skipFetch) { var currentId = this.gCurrentId; if (currentId == null) { @@ -80,6 +81,17 @@ var UserStore = assign({}, EventEmitter.prototype, { this.gCurrentId = currentId; } + // this is a special case to force fetch the + // current user if it's missing + // it's synchronous to block rendering + if (currentId == null && !skipFetch) { + var me = client.getMeSynchronous(); + if (me != null) { + this.setCurrentUser(me); + currentId = me.id; + } + } + return currentId; }, getCurrentUser: function() { |