From 5cfced8a33a5f8eaa14e0549ee4b013bafa0833c Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Tue, 27 Apr 2021 16:38:20 -0700 Subject: Added badges to store --- src/store/initialStates.ts | 1 + src/store/reducers/userReducer.ts | 5 +++++ src/types/types.ts | 1 + 3 files changed, 7 insertions(+) (limited to 'src') diff --git a/src/store/initialStates.ts b/src/store/initialStates.ts index 7fd3ac5a..e0f9d776 100644 --- a/src/store/initialStates.ts +++ b/src/store/initialStates.ts @@ -18,6 +18,7 @@ export const NO_PROFILE: ProfileInfoType = { birthday: undefined, university_class: 2021, university: undefined, + badges: [], //Default to an invalid value and ignore it gracefully while showing tutorials / popups. profile_completion_stage: -1, suggested_people_linked: -1, diff --git a/src/store/reducers/userReducer.ts b/src/store/reducers/userReducer.ts index a8789c1d..97bf845c 100644 --- a/src/store/reducers/userReducer.ts +++ b/src/store/reducers/userReducer.ts @@ -42,6 +42,10 @@ const userDataSlice = createSlice({ } }, + profileBadgesUpdated: (state, action) => { + state.profile.badges = action.payload.badges; + }, + profileCompletionStageUpdated: (state, action) => { state.profile.profile_completion_stage = action.payload.stage; }, @@ -90,6 +94,7 @@ export const { setReplyPosted, setSuggestedPeopleImage, clearHeaderAndProfileImages, + profileBadgesUpdated, // setChatClientReady, } = userDataSlice.actions; export const userDataReducer = userDataSlice.reducer; diff --git a/src/types/types.ts b/src/types/types.ts index e7f651dc..18ddbfba 100644 --- a/src/types/types.ts +++ b/src/types/types.ts @@ -46,6 +46,7 @@ export interface ProfileInfoType { gender: string; university_class: number; university: UniversityType; + badges: UniversityBadge[]; profile_completion_stage: number; suggested_people_linked: number; birthday: Date | undefined; -- cgit v1.2.3-70-g09d2 From 20d2c580dd9576a3cfd95543300d7735157a3494 Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Tue, 27 Apr 2021 17:51:55 -0700 Subject: Added action to update badges --- src/store/actions/user.ts | 22 +++++++++++++++++++++- 1 file changed, 21 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/store/actions/user.ts b/src/store/actions/user.ts index 3ebd4190..96e636f6 100644 --- a/src/store/actions/user.ts +++ b/src/store/actions/user.ts @@ -6,10 +6,11 @@ import { loadProfileInfo, sendSuggestedPeopleLinked, } from '../../services'; -import {UserType} from '../../types/types'; +import {UniversityBadge, UserType} from '../../types/types'; import {getTokenOrLogout} from '../../utils'; import { clearHeaderAndProfileImages, + profileBadgesUpdated, profileCompletionStageUpdated, setIsOnboardedUser, setNewNotificationReceived, @@ -90,6 +91,25 @@ export const updateSocial = ( } }; +/** + * To update new user badges + * @param badges current selection of badges + */ +export const updateUserBadges = ( + badges: UniversityBadge[], +): ThunkAction, RootState, unknown, Action> => async ( + dispatch, +) => { + try { + dispatch({ + type: profileBadgesUpdated.type, + payload: {badges}, + }); + } catch (error) { + console.log(error); + } +}; + export const updateProfileCompletionStage = ( stage: number, ): ThunkAction, RootState, unknown, Action> => async ( -- cgit v1.2.3-70-g09d2 From bf126bc7618278f3300d45897fd3e196a551445f Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Tue, 27 Apr 2021 17:53:11 -0700 Subject: removed loading icon, fetching badges from store --- src/components/common/BadgeDetailView.tsx | 89 +++++++++---------------------- 1 file changed, 24 insertions(+), 65 deletions(-) (limited to 'src') diff --git a/src/components/common/BadgeDetailView.tsx b/src/components/common/BadgeDetailView.tsx index bc4384e8..6504300c 100644 --- a/src/components/common/BadgeDetailView.tsx +++ b/src/components/common/BadgeDetailView.tsx @@ -1,24 +1,15 @@ import {useNavigation} from '@react-navigation/core'; import React, {useEffect, useState} from 'react'; -import { - ActivityIndicator, - FlatList, - Image, - Modal, - StyleSheet, - Text, - View, -} from 'react-native'; +import {FlatList, Image, Modal, StyleSheet, Text, View} from 'react-native'; import {TouchableOpacity} from 'react-native-gesture-handler'; import LinearGradient from 'react-native-linear-gradient'; -import {useSelector} from 'react-redux'; +import {useDispatch, useSelector} from 'react-redux'; import CloseIcon from '../../assets/ionicons/close-outline.svg'; import {BADGE_GRADIENT_FIRST} from '../../constants'; import {BADGE_DATA} from '../../constants/badges'; -import {getSuggestedPeopleProfile, removeBadgesService} from '../../services'; import {RootState} from '../../store/rootreducer'; -import {ScreenType, UniversityBadge} from '../../types'; -import {getUniversityBadge, normalize} from '../../utils'; +import {ScreenType} from '../../types'; +import {getUniversityBadge, normalize, removeUserBadge} from '../../utils'; interface BadgeDetailModalProps { userXId: string | undefined; @@ -35,38 +26,21 @@ const BadgeDetailView: React.FC = ({ isEditable = true, setBadgeViewVisible, }) => { - const {user, profile} = useSelector((state: RootState) => + const dispatch = useDispatch(); + const { + user, + profile: {university, badges}, + } = useSelector((state: RootState) => userXId ? state.userX[screenType][userXId] : state.user, ); const navigation = useNavigation(); - const [selectedBadges, setSelectedBadges] = useState([]); - const [isLoading, setIsLoading] = useState(true); const [selectedBadgesWithImage, setSelectedBadgesWithImage] = useState( [], ); - const fetchBadges = async () => { - if (user.userId) { - const response = await getSuggestedPeopleProfile(user.userId); - if (response) { - const data = response.badges; - let extractedBadgeNames: UniversityBadge[] = []; - data.forEach((badge) => { - extractedBadgeNames.push(badge); - }); - setSelectedBadges(extractedBadgeNames); - } - } - }; - - useEffect(() => { - setIsLoading(true); - fetchBadges(); - }, []); - useEffect(() => { let badgesWithImage = []; - selectedBadges.forEach((e) => { + badges.forEach((e) => { const uniData = BADGE_DATA[e.university]; const categoryData = uniData.filter((u) => { return u.title === e.category; @@ -81,14 +55,11 @@ const BadgeDetailView: React.FC = ({ }); setTimeout(() => { setSelectedBadgesWithImage(badgesWithImage); - setIsLoading(false); }, 250); - }, [selectedBadges]); + }, [badges]); - const removeBadgeCell = async (badge: string) => { - setIsLoading(true); - await removeBadgesService([badge], user.userId); - fetchBadges(); + const removeBadgeCell = async (badgeName: string) => { + await removeUserBadge(badges, badgeName, user.userId, dispatch); }; const badgeEditCell = ({item: {id, name, badgeImage}}) => { @@ -175,38 +146,27 @@ const BadgeDetailView: React.FC = ({ {modalHeader()} - {!isLoading && ( - - item.id.toString()} - /> - - )} - {isLoading && _loaderView()} + + item.id.toString()} + /> + {isEditable && addButton()} ); }; - const _loaderView = () => { - return ( - - - - ); - }; - return ( Date: Tue, 27 Apr 2021 17:56:21 -0700 Subject: func to call remove badge serv, dispatch action --- src/utils/users.ts | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/utils/users.ts b/src/utils/users.ts index 7148eb79..87bcbdfc 100644 --- a/src/utils/users.ts +++ b/src/utils/users.ts @@ -1,6 +1,6 @@ import AsyncStorage from '@react-native-community/async-storage'; import {INTEGRATED_SOCIAL_LIST} from '../constants'; -import {isUserBlocked, loadSocialPosts} from '../services'; +import {isUserBlocked, loadSocialPosts, removeBadgesService} from '../services'; import { loadAllSocials, loadBlockedList, @@ -10,6 +10,7 @@ import { loadUserMoments, loadUserNotifications, logout, + updateUserBadges, } from '../store/actions'; import {NO_SOCIAL_ACCOUNTS} from '../store/initialStates'; import {loadUserMomentCategories} from './../store/actions/momentCategories'; @@ -21,6 +22,7 @@ import { ProfileInfoType, ScreenType, UserType, + UniversityBadge, } from './../types/types'; const loadData = async (dispatch: AppDispatch, user: UserType) => { @@ -204,3 +206,20 @@ export const canViewProfile = ( } return false; }; + +/* Function to call remove badge service, + * remove selected badge from list passed in and + * dispatch thunk action to update store + */ +export const removeUserBadge = async ( + badges: UniversityBadge[], + badgeName: string, + userId: string, + dispatch: AppDispatch, +) => { + const success = await removeBadgesService([badgeName], userId); + if (success === true) { + badges = badges.filter((badge) => badge.name !== badgeName); + dispatch(updateUserBadges(badges)); + } +}; -- cgit v1.2.3-70-g09d2 From 8cd2121c220b31c61b7936d6c728aae7f7177c4b Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Wed, 28 Apr 2021 07:18:39 -0700 Subject: added get get_badges endpoint and service --- src/constants/api.ts | 1 + src/services/SuggestedPeopleService.ts | 37 +++++++++++++++++++++++++++++++--- 2 files changed, 35 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/constants/api.ts b/src/constants/api.ts index 45b6e8ae..d45616a1 100644 --- a/src/constants/api.ts +++ b/src/constants/api.ts @@ -60,6 +60,7 @@ export const UPDATE_BADGES_ENDPOINT: string = SP_USERS_ENDPOINT + 'update_badges/'; export const REMOVE_BADGES_ENDPOINT: string = SP_USERS_ENDPOINT + 'remove_badges/'; +export const GET_USER_BADGES_ENDPOINT: string = SP_USERS_ENDPOINT + 'get_badges/'; // Register as FCM device export const FCM_ENDPOINT: string = API_URL + 'fcm/'; diff --git a/src/services/SuggestedPeopleService.ts b/src/services/SuggestedPeopleService.ts index 7f5b4b8c..bdcbc437 100644 --- a/src/services/SuggestedPeopleService.ts +++ b/src/services/SuggestedPeopleService.ts @@ -7,13 +7,18 @@ import { import { ADD_BADGES_ENDPOINT, EDIT_PROFILE_ENDPOINT, + GET_USER_BADGES_ENDPOINT, REMOVE_BADGES_ENDPOINT, SP_MUTUAL_BADGE_HOLDERS_ENDPOINT, SP_UPDATE_PICTURE_ENDPOINT, SP_USERS_ENDPOINT, UPDATE_BADGES_ENDPOINT, } from '../constants/api'; -import {ProfilePreviewType, SuggestedPeopleDataType} from '../types'; +import { + ProfilePreviewType, + SuggestedPeopleDataType, + UniversityBadge, +} from '../types'; import {Alert} from 'react-native'; export const sendSuggestedPeopleLinked = async ( @@ -166,6 +171,31 @@ export const addBadgesService = async ( } }; +export const getBadgesService = async (userId: string) => { + try { + const token = await AsyncStorage.getItem('token'); + const response = await fetch( + GET_USER_BADGES_ENDPOINT + '?user_id=' + userId, + { + method: 'GET', + headers: { + Authorization: 'Token ' + token, + }, + }, + ); + if (response.status === 200) { + const data: UniversityBadge[] = await response.json(); + return data ? data : []; + } else { + console.log('Error loading badges data'); + return []; + } + } catch (error) { + console.log('Exception occued while loading badges data, ', error); + return []; + } +}; + export const updateBadgesService = async ( selectedBadges: string[], university: string, @@ -216,14 +246,15 @@ export const removeBadgesService = async ( }); if (response.status === 400) { Alert.alert(ERROR_BADGES_EXCEED_LIMIT); - return; + return false; } if (response.status === 200) { Alert.alert(SUCCESS_BADGES_UPDATE); - return; + return true; } } catch (error) { console.log(error); Alert.alert(ERROR_UPLOAD_BADGES); + return false; } }; -- cgit v1.2.3-70-g09d2 From 30ab35a80b34608243836b463d40cd50fecbdbf8 Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Wed, 28 Apr 2021 07:22:42 -0700 Subject: badge selection to load badge data after upadte --- src/screens/badge/BadgeSelection.tsx | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) (limited to 'src') diff --git a/src/screens/badge/BadgeSelection.tsx b/src/screens/badge/BadgeSelection.tsx index 38a2b01c..66dca509 100644 --- a/src/screens/badge/BadgeSelection.tsx +++ b/src/screens/badge/BadgeSelection.tsx @@ -12,10 +12,13 @@ import {ERROR_BADGES_EXCEED_LIMIT} from '../../constants/strings'; import {MainStackParams} from '../../routes'; import { addBadgesService, - getSuggestedPeopleProfile, + getBadgesService, updateBadgesService, } from '../../services'; -import {suggestedPeopleBadgesFinished} from '../../store/actions'; +import { + suggestedPeopleBadgesFinished, + updateUserBadges, +} from '../../store/actions'; import {RootState} from '../../store/rootReducer'; import {BackgroundGradientType} from '../../types'; import {SCREEN_HEIGHT, StatusBarHeight} from '../../utils'; @@ -36,30 +39,32 @@ const BadgeSelection: React.FC = ({route}) => { const {editing} = route.params; const { user: {userId: loggedInUserId}, - profile: {university}, + profile: {university, badges}, } = useSelector((state: RootState) => state.user); const [selectedBadges, setSelectedBadges] = useState([]); const dispatch = useDispatch(); const navigation = useNavigation(); - // Loading badges data and extracting into a string [] + // Extracting badges data into a string [] useEffect(() => { const loadData = async () => { - const response = await getSuggestedPeopleProfile(loggedInUserId); - if (response) { - const data = response.badges; - let extractedBadgeNames: string[] = []; - data.forEach((badge) => { - extractedBadgeNames.push(badge.name); - }); - setSelectedBadges(extractedBadgeNames); - } + let extractedBadgeNames: string[] = []; + badges.forEach((badge) => { + extractedBadgeNames.push(badge.name); + }); + setSelectedBadges(extractedBadgeNames); }; if (editing) { loadData(); } }, []); + // Retrieve updated badges using get badges service and udpate the store + const loadUserBadges = async () => { + const newBadges = await getBadgesService(loggedInUserId); + dispatch(updateUserBadges(newBadges)); + }; + navigation.setOptions({ headerRight: () => ( = ({route}) => { onPress={async () => { if (editing) { await updateBadgesService(selectedBadges, university); + // Load updated badges to store + loadUserBadges(); if (navigation.canGoBack()) { navigation.goBack(); } else { @@ -82,6 +89,7 @@ const BadgeSelection: React.FC = ({route}) => { ); if (success) { dispatch(suggestedPeopleBadgesFinished()); + loadUserBadges(); navigation.navigate('SuggestedPeople'); } } else { -- cgit v1.2.3-70-g09d2 From 65c7411f4609edac3d4d5f23fc031ed274fc5872 Mon Sep 17 00:00:00 2001 From: Shravya Ramesh Date: Wed, 28 Apr 2021 07:27:36 -0700 Subject: alerts rearranged --- src/screens/badge/BadgeSelection.tsx | 17 +++++++++++++---- src/services/SuggestedPeopleService.ts | 7 ++----- 2 files changed, 15 insertions(+), 9 deletions(-) (limited to 'src') diff --git a/src/screens/badge/BadgeSelection.tsx b/src/screens/badge/BadgeSelection.tsx index 66dca509..d0dcfa4c 100644 --- a/src/screens/badge/BadgeSelection.tsx +++ b/src/screens/badge/BadgeSelection.tsx @@ -8,7 +8,10 @@ import LinearGradient from 'react-native-linear-gradient'; import {useDispatch, useSelector} from 'react-redux'; import {BACKGROUND_GRADIENT_MAP} from '../../constants'; import {BADGE_DATA} from '../../constants/badges'; -import {ERROR_BADGES_EXCEED_LIMIT} from '../../constants/strings'; +import { + ERROR_BADGES_EXCEED_LIMIT, + SUCCESS_BADGES_UPDATE, +} from '../../constants/strings'; import {MainStackParams} from '../../routes'; import { addBadgesService, @@ -71,9 +74,15 @@ const BadgeSelection: React.FC = ({route}) => { style={styles.rightButtonContainer} onPress={async () => { if (editing) { - await updateBadgesService(selectedBadges, university); - // Load updated badges to store - loadUserBadges(); + const success = await updateBadgesService( + selectedBadges, + university, + ); + if (success === true) { + // Load updated badges to store + loadUserBadges(); + Alert.alert(SUCCESS_BADGES_UPDATE); + } if (navigation.canGoBack()) { navigation.goBack(); } else { diff --git a/src/services/SuggestedPeopleService.ts b/src/services/SuggestedPeopleService.ts index bdcbc437..2ae8cf55 100644 --- a/src/services/SuggestedPeopleService.ts +++ b/src/services/SuggestedPeopleService.ts @@ -2,7 +2,6 @@ import AsyncStorage from '@react-native-community/async-storage'; import { ERROR_BADGES_EXCEED_LIMIT, ERROR_UPLOAD_BADGES, - SUCCESS_BADGES_UPDATE, } from '../constants/strings'; import { ADD_BADGES_ENDPOINT, @@ -215,11 +214,10 @@ export const updateBadgesService = async ( }); if (response.status === 400) { Alert.alert(ERROR_BADGES_EXCEED_LIMIT); - return; + return false; } if (response.status === 200) { - Alert.alert(SUCCESS_BADGES_UPDATE); - return; + return true; } } catch (error) { console.log(error); @@ -249,7 +247,6 @@ export const removeBadgesService = async ( return false; } if (response.status === 200) { - Alert.alert(SUCCESS_BADGES_UPDATE); return true; } } catch (error) { -- cgit v1.2.3-70-g09d2