@@ -8,8 +8,11 @@ import awais.instagrabber.db.entities.Favorite
8
8
import awais.instagrabber.db.repositories.AccountRepository
9
9
import awais.instagrabber.db.repositories.FavoriteRepository
10
10
import awais.instagrabber.managers.DirectMessagesManager
11
+ import awais.instagrabber.models.HighlightModel
11
12
import awais.instagrabber.models.Resource
13
+ import awais.instagrabber.models.StoryModel
12
14
import awais.instagrabber.models.enums.FavoriteType
15
+ import awais.instagrabber.repositories.requests.StoryViewerOptions
13
16
import awais.instagrabber.repositories.responses.User
14
17
import awais.instagrabber.repositories.responses.directmessages.RankedRecipient
15
18
import awais.instagrabber.utils.ControlledRunner
@@ -22,7 +25,7 @@ class ProfileFragmentViewModel(
22
25
state : SavedStateHandle ,
23
26
userRepository : UserRepository ,
24
27
friendshipRepository : FriendshipRepository ,
25
- storiesRepository : StoriesRepository ,
28
+ private val storiesRepository : StoriesRepository ,
26
29
mediaRepository : MediaRepository ,
27
30
graphQLRepository : GraphQLRepository ,
28
31
accountRepository : AccountRepository ,
@@ -61,27 +64,21 @@ class ProfileFragmentViewModel(
61
64
62
65
private val profileFetchControlledRunner = ControlledRunner <User ?>()
63
66
val profile: LiveData <Resource <User ?>> = currentUserAndStateUsernameLiveData.switchMap {
64
- val (userResource , stateUsernameResource) = it
67
+ val (currentUserResource , stateUsernameResource) = it
65
68
liveData<Resource <User ?>>(context = viewModelScope.coroutineContext + ioDispatcher) {
66
- if (userResource .status == Resource .Status .LOADING || stateUsernameResource.status == Resource .Status .LOADING ) {
69
+ if (currentUserResource .status == Resource .Status .LOADING || stateUsernameResource.status == Resource .Status .LOADING ) {
67
70
emit(Resource .loading(null ))
68
71
return @liveData
69
72
}
70
- val user = userResource .data
73
+ val currentUser = currentUserResource .data
71
74
val stateUsername = stateUsernameResource.data
72
75
if (stateUsername.isNullOrBlank()) {
73
- emit(Resource .success(user ))
76
+ emit(Resource .success(currentUser ))
74
77
return @liveData
75
78
}
76
79
try {
77
80
val fetchedUser = profileFetchControlledRunner.cancelPreviousThenRun {
78
- return @cancelPreviousThenRun if (user != null ) {
79
- val tempUser = userRepository.getUsernameInfo(stateUsername) // logged in
80
- tempUser.friendshipStatus = userRepository.getUserFriendship(tempUser.pk)
81
- return @cancelPreviousThenRun tempUser
82
- } else {
83
- graphQLRepository.fetchUser(stateUsername) // anonymous
84
- }
81
+ return @cancelPreviousThenRun fetchUser(currentUser, userRepository, stateUsername, graphQLRepository)
85
82
}
86
83
emit(Resource .success(fetchedUser))
87
84
if (fetchedUser != null ) {
@@ -94,6 +91,81 @@ class ProfileFragmentViewModel(
94
91
}
95
92
}
96
93
94
+ private val storyFetchControlledRunner = ControlledRunner <List <StoryModel >? > ()
95
+ val userStories: LiveData <Resource <List <StoryModel >? >> = profile.switchMap { userResource ->
96
+ liveData<Resource <List <StoryModel >? >> (context = viewModelScope.coroutineContext + ioDispatcher) {
97
+ // don't fetch if not logged in
98
+ if (isLoggedIn.value != true ) {
99
+ emit(Resource .success(null ))
100
+ return @liveData
101
+ }
102
+ if (userResource.status == Resource .Status .LOADING ) {
103
+ emit(Resource .loading(null ))
104
+ return @liveData
105
+ }
106
+ val user = userResource.data
107
+ if (user == null ) {
108
+ emit(Resource .success(null ))
109
+ return @liveData
110
+ }
111
+ try {
112
+ val fetchedStories = storyFetchControlledRunner.cancelPreviousThenRun { fetchUserStory(user) }
113
+ emit(Resource .success(fetchedStories))
114
+ } catch (e: Exception ) {
115
+ emit(Resource .error(e.message, null ))
116
+ Log .e(TAG , " fetching story: " , e)
117
+ }
118
+ }
119
+ }
120
+
121
+ private val highlightsFetchControlledRunner = ControlledRunner <List <HighlightModel >? > ()
122
+ val userHighlights: LiveData <Resource <List <HighlightModel >? >> = profile.switchMap { userResource ->
123
+ liveData<Resource <List <HighlightModel >? >> (context = viewModelScope.coroutineContext + ioDispatcher) {
124
+ // don't fetch if not logged in
125
+ if (isLoggedIn.value != true ) {
126
+ emit(Resource .success(null ))
127
+ return @liveData
128
+ }
129
+ if (userResource.status == Resource .Status .LOADING ) {
130
+ emit(Resource .loading(null ))
131
+ return @liveData
132
+ }
133
+ val user = userResource.data
134
+ if (user == null ) {
135
+ emit(Resource .success(null ))
136
+ return @liveData
137
+ }
138
+ try {
139
+ val fetchedHighlights = highlightsFetchControlledRunner.cancelPreviousThenRun { fetchUserHighlights(user) }
140
+ emit(Resource .success(fetchedHighlights))
141
+ } catch (e: Exception ) {
142
+ emit(Resource .error(e.message, null ))
143
+ Log .e(TAG , " fetching story: " , e)
144
+ }
145
+ }
146
+ }
147
+
148
+ private suspend fun fetchUser (
149
+ currentUser : User ? ,
150
+ userRepository : UserRepository ,
151
+ stateUsername : String ,
152
+ graphQLRepository : GraphQLRepository
153
+ ) = if (currentUser != null ) {
154
+ // logged in
155
+ val tempUser = userRepository.getUsernameInfo(stateUsername)
156
+ tempUser.friendshipStatus = userRepository.getUserFriendship(tempUser.pk)
157
+ tempUser
158
+ } else {
159
+ // anonymous
160
+ graphQLRepository.fetchUser(stateUsername)
161
+ }
162
+
163
+ private suspend fun fetchUserStory (fetchedUser : User ): List <StoryModel > = storiesRepository.getUserStory(
164
+ StoryViewerOptions .forUser(fetchedUser.pk, fetchedUser.fullName)
165
+ )
166
+
167
+ private suspend fun fetchUserHighlights (fetchedUser : User ): List <HighlightModel > = storiesRepository.fetchHighlights(fetchedUser.pk)
168
+
97
169
private suspend fun checkAndInsertFavorite (fetchedUser : User ) {
98
170
try {
99
171
val favorite = favoriteRepository.getFavorite(fetchedUser.username, FavoriteType .USER )
0 commit comments