From 4bc4df866beaf8418874fc902d5a9ec76ddd7890 Mon Sep 17 00:00:00 2001 From: Ryan Baer Date: Thu, 26 Oct 2017 11:57:21 -0700 Subject: [PATCH] Fix for #810: followed user appears among recs after reloading the page (#893) * Fix for #810: followed user appears among recs after reloading the page --- src/app/Sidebar/RightSidebar.js | 41 ++++++--------------- src/components/Sidebar/InterestingPeople.js | 2 +- src/reducers.js | 1 + src/user/userActions.js | 4 ++ src/user/userReducer.js | 23 +++++++++++- 5 files changed, 40 insertions(+), 31 deletions(-) diff --git a/src/app/Sidebar/RightSidebar.js b/src/app/Sidebar/RightSidebar.js index 31d1130978..6ce8c1c818 100644 --- a/src/app/Sidebar/RightSidebar.js +++ b/src/app/Sidebar/RightSidebar.js @@ -2,14 +2,14 @@ import React from 'react'; import PropTypes from 'prop-types'; import { connect } from 'react-redux'; import { Route, Switch } from 'react-router-dom'; -import people from '../../helpers/people'; import { getIsAuthenticated, getAuthenticatedUser, - getFollowingList, getIsAuthFetching, + getRecommendations, } from '../../reducers'; +import { updateRecommendations } from '../../user/userActions'; import InterestingPeople from '../../components/Sidebar/InterestingPeople'; import StartNow from '../../components/Sidebar/StartNow'; @@ -20,52 +20,35 @@ import PostRecommendation from '../../components/Sidebar/PostRecommendation'; state => ({ authenticated: getIsAuthenticated(state), authenticatedUser: getAuthenticatedUser(state), - followingList: getFollowingList(state), isAuthFetching: getIsAuthFetching(state), - }), + recommendations: getRecommendations(state), + }), { + updateRecommendations, + }, ) export default class RightSidebar extends React.Component { static propTypes = { authenticated: PropTypes.bool.isRequired, authenticatedUser: PropTypes.shape().isRequired, - followingList: PropTypes.arrayOf(PropTypes.string).isRequired, isAuthFetching: PropTypes.bool.isRequired, showPostRecommendation: PropTypes.bool, + recommendations: PropTypes.arrayOf(PropTypes.shape({ name: PropTypes.string })).isRequired, + updateRecommendations: PropTypes.func, }; static defaultProps = { showPostRecommendation: false, + updateRecommendations: () => {}, }; - constructor(props) { - super(props); - this.state = { - randomPeople: this.getRandomPeople(), - }; - } - - getRandomPeople = () => - people - .reduce((res, item) => { - if (!this.props.followingList.includes(item)) { - res.push({ name: item }); - } - return res; - }, []) - .sort(() => 0.5 - Math.random()) - .slice(0, 5); - - handleRefreshInterestingPeople = () => - this.setState({ - randomPeople: this.getRandomPeople(), - }); + handleInterestingPeopleRefresh = () => this.props.updateRecommendations(); render() { const { authenticated, authenticatedUser, showPostRecommendation, isAuthFetching } = this.props; const InterestingPeopleWithData = () => ( ); diff --git a/src/components/Sidebar/InterestingPeople.js b/src/components/Sidebar/InterestingPeople.js index ba7b6c6f62..08265675a5 100644 --- a/src/components/Sidebar/InterestingPeople.js +++ b/src/components/Sidebar/InterestingPeople.js @@ -29,7 +29,7 @@ const InterestingPeople = ({ users, onRefresh }) => ); InterestingPeople.propTypes = { - users: PropTypes.arrayOf(PropTypes.shape()), + users: PropTypes.arrayOf(PropTypes.shape({ name: PropTypes.string })), onRefresh: PropTypes.func, }; diff --git a/src/reducers.js b/src/reducers.js index 44400b7afe..f5509e2478 100644 --- a/src/reducers.js +++ b/src/reducers.js @@ -78,6 +78,7 @@ export const getPendingReblogs = state => fromReblog.getPendingReblogs(state.reb export const getFollowingList = state => fromUser.getFollowingList(state.user); export const getPendingFollows = state => fromUser.getPendingFollows(state.user); +export const getRecommendations = state => fromUser.getRecommendations(state.user); export const getUser = (state, username) => fromUsers.getUser(state.users, username); diff --git a/src/user/userActions.js b/src/user/userActions.js index ce21601e23..ca2c406abd 100644 --- a/src/user/userActions.js +++ b/src/user/userActions.js @@ -1,5 +1,6 @@ import Promise from 'bluebird'; import steemConnect from 'sc2-sdk'; +import { createAction } from 'redux-actions'; import { getFeed, getPosts } from '../reducers'; import { getUserCommentsFromState, getFeedLoadingFromState } from '../helpers/stateHelpers'; import { getAllFollowing } from '../helpers/apiHelpers'; @@ -133,3 +134,6 @@ export const getFollowing = (userName = '') => (dispatch, getState) => { }, }); }; + +export const UPDATE_RECOMMENDATIONS = '@user/UPDATE_RECOMMENDATIONS'; +export const updateRecommendations = createAction(UPDATE_RECOMMENDATIONS); diff --git a/src/user/userReducer.js b/src/user/userReducer.js index 6c6de76b32..8c6372ee45 100644 --- a/src/user/userReducer.js +++ b/src/user/userReducer.js @@ -1,6 +1,6 @@ import keyBy from 'lodash/keyBy'; import omit from 'lodash/omit'; - +import people from '../helpers/people'; import * as actions from './userActions'; const initialState = { @@ -12,6 +12,7 @@ const initialState = { fileUploadError: null, filesFetchError: null, filesFetchIsLoading: true, + recommendations: [], following: { list: [], pendingFollows: [], @@ -19,6 +20,17 @@ const initialState = { }, }; +// filterRecommendations generates a random list of `count` recommendations +// include users followed by the current user. +const filterRecommendations = (following, count = 5) => { + const usernames = Object.values(following); + return people + .filter(p => !usernames.includes(p)) + .sort(() => 0.5 - Math.random()) + .slice(0, count) + .map(name => ({ name })); +}; + export default function userReducer(state = initialState, action) { switch (action.type) { case actions.UPLOAD_FILE_START: { @@ -92,6 +104,7 @@ export default function userReducer(state = initialState, action) { case actions.GET_FOLLOWING_SUCCESS: return { ...state, + recommendations: filterRecommendations(action.payload), following: { ...state.following, list: action.payload, @@ -141,6 +154,13 @@ export default function userReducer(state = initialState, action) { ), }, }; + + case actions.UPDATE_RECOMMENDATIONS: + return { + ...state, + recommendations: filterRecommendations(state.following.list), + }; + default: { return state; } @@ -149,3 +169,4 @@ export default function userReducer(state = initialState, action) { export const getFollowingList = state => state.following.list; export const getPendingFollows = state => state.following.pendingFollows; +export const getRecommendations = state => state.recommendations;