diff --git a/app/soapbox/actions/streaming.js b/app/soapbox/actions/streaming.js index 1baa252b0..3f5473811 100644 --- a/app/soapbox/actions/streaming.js +++ b/app/soapbox/actions/streaming.js @@ -13,6 +13,7 @@ import { getSettings } from 'soapbox/actions/settings'; import messages from 'soapbox/locales/messages'; export const STREAMING_CHAT_UPDATE = 'STREAMING_CHAT_UPDATE'; +export const STREAMING_FOLLOW_RELATIONSHIPS_UPDATE = 'STREAMING_FOLLOW_RELATIONSHIPS_UPDATE'; const validLocale = locale => Object.keys(messages).includes(locale); @@ -21,6 +22,17 @@ const getLocale = state => { return validLocale(locale) ? locale : 'en'; }; +function updateFollowRelationships(relationships) { + return (dispatch, getState) => { + const me = getState().get('me'); + return dispatch({ + type: STREAMING_FOLLOW_RELATIONSHIPS_UPDATE, + me, + ...relationships, + }); + }; +} + export function connectTimelineStream(timelineId, path, pollingRefresh = null, accept = null) { return connectStream (path, pollingRefresh, (dispatch, getState) => { @@ -69,6 +81,9 @@ export function connectTimelineStream(timelineId, path, pollingRefresh = null, a }); }); break; + case 'pleroma:follow_relationships_update': + dispatch(updateFollowRelationships(JSON.parse(data.payload))); + break; } }, }; diff --git a/app/soapbox/reducers/accounts_counters.js b/app/soapbox/reducers/accounts_counters.js index 9ebf72af9..0d54c1207 100644 --- a/app/soapbox/reducers/accounts_counters.js +++ b/app/soapbox/reducers/accounts_counters.js @@ -3,6 +3,7 @@ import { ACCOUNT_UNFOLLOW_SUCCESS, } from '../actions/accounts'; import { ACCOUNT_IMPORT, ACCOUNTS_IMPORT } from '../actions/importer'; +import { STREAMING_FOLLOW_RELATIONSHIPS_UPDATE } from 'soapbox/actions/streaming'; import { Map as ImmutableMap, fromJS } from 'immutable'; const normalizeAccount = (state, account) => state.set(account.id, fromJS({ @@ -19,6 +20,17 @@ const normalizeAccounts = (state, accounts) => { return state; }; +const updateFollowCounters = (state, counterUpdates) => { + return state.withMutations(state => { + counterUpdates.forEach(counterUpdate => { + state.update(counterUpdate.id, ImmutableMap(), counters => counters.merge({ + followers_count: counterUpdate.follower_count, + following_count: counterUpdate.following_count, + })); + }); + }); +}; + const initialState = ImmutableMap(); export default function accountsCounters(state = initialState, action) { @@ -32,6 +44,8 @@ export default function accountsCounters(state = initialState, action) { state.updateIn([action.relationship.id, 'followers_count'], num => num + 1); case ACCOUNT_UNFOLLOW_SUCCESS: return state.updateIn([action.relationship.id, 'followers_count'], num => Math.max(0, num - 1)); + case STREAMING_FOLLOW_RELATIONSHIPS_UPDATE: + return updateFollowCounters(state, [action.follower, action.following]); default: return state; } diff --git a/app/soapbox/reducers/relationships.js b/app/soapbox/reducers/relationships.js index dfc93950b..032582bc1 100644 --- a/app/soapbox/reducers/relationships.js +++ b/app/soapbox/reducers/relationships.js @@ -21,6 +21,7 @@ import { DOMAIN_BLOCK_SUCCESS, DOMAIN_UNBLOCK_SUCCESS, } from '../actions/domain_blocks'; +import { STREAMING_FOLLOW_RELATIONSHIPS_UPDATE } from 'soapbox/actions/streaming'; import { Map as ImmutableMap, fromJS } from 'immutable'; import { get } from 'lodash'; @@ -57,6 +58,24 @@ const importPleromaAccounts = (state, accounts) => { return state; }; +const followStateToRelationship = followState => { + switch(followState) { + case 'follow_pending': + return { following: false, requested: true }; + case 'follow_accept': + return { following: true, requested: false }; + case 'follow_reject': + return { following: false, requested: false }; + default: + return {}; + } +}; + +const updateFollowRelationship = (state, id, followState) => { + const map = followStateToRelationship(followState); + return state.update(id, ImmutableMap(), relationship => relationship.merge(map)); +}; + const initialState = ImmutableMap(); export default function relationships(state = initialState, action) { @@ -66,9 +85,9 @@ export default function relationships(state = initialState, action) { case ACCOUNTS_IMPORT: return importPleromaAccounts(state, action.accounts); case ACCOUNT_FOLLOW_REQUEST: - return state.setIn([action.id, action.locked ? 'requested' : 'following'], true); + return state.setIn([action.id, 'requested'], true); case ACCOUNT_FOLLOW_FAIL: - return state.setIn([action.id, action.locked ? 'requested' : 'following'], false); + return state.setIn([action.id, 'requested'], false); case ACCOUNT_UNFOLLOW_REQUEST: return state.setIn([action.id, 'following'], false); case ACCOUNT_UNFOLLOW_FAIL: @@ -88,6 +107,12 @@ export default function relationships(state = initialState, action) { return setDomainBlocking(state, action.accounts, true); case DOMAIN_UNBLOCK_SUCCESS: return setDomainBlocking(state, action.accounts, false); + case STREAMING_FOLLOW_RELATIONSHIPS_UPDATE: + if (action.follower.id === action.me) { + return updateFollowRelationship(state, action.following.id, action.state); + } else { + return state; + } default: return state; }