Update Controller with new resolved value


#1

Hello gents, i have this scenario .
i have state that get data from back end database , first time the resolved value captured correctly and i can see this value in my controller , next time , when this value changed in the back end Db , the new resolved value is not updated in my controller , it seems the controller not Re-initiated after state changed to , i tried to use disable cache , it works but this is not the aim of my app , this way i am killing the performance , i tried to use $apply with no luck , i found this post $state.reload() should reinitialize the controller and it describes the issue i have , none of these solutions works for me , did anyone ran into this issue ? i need the new resolved value captured in my controller and stay sync with the value in my backend


#2

Two solutions:

  1. Use sockets to emit any updates on the server to the app. For example, if I update a field on the backend, this update would emit to all connected sockets, and then you could update your controller on socket message.

  2. Use the ionic lifecycle events. In you situation, I would use the $ionicView.enter, which will fire everytime you enter the view, so you can still cache the view and you no longer need to call $state.reload().

I’d say the socket approach would be the most difficult since you need to setup the server to allow for sockets which can be tricky, but this is also how you would achieve almost instantaneous updates. Its what I use for a real-time chat app and works great.

The second approach would be the easiest, but it would cause a delay in the time the user navigates to the view and when the data is refreshed.

To implement the second approach, in your controller you would add something like:

$scope.$on('$ionicView.enter', function(){
//Get data
});

Also, here is a great article that I refrence for ionic lifecycle events
Ionic Lifecycle Events


#3

Many thanks @DaDanny , it seems using on enter event is the most appropriate solution at the moment , i implement it this way , first time i i will receive the value on state rout and then i do double check every time the state changed with the resolved value if they equal no need to update the DOM variable if not i made request to the server to capture the updated ones and update the DOM variable , it seems it is a bug in ui-rout , the expected behavior , every time new value resolved it should be detected and reload the state when routing which will update the DOM too , may be using this $state.go(state-name ,{reload:true}) would solve the issue but how to use it in tab application as tabs app not the same of single app page navigation .


#4

I wouldn’t use the ui-router resolve function at all in this case.

When the user clicks on a tab, the view + controller will be loaded and your ionicEvent.enter will fire. When this event fires, I would display something to the user, like a loading icon, so they know you are refreshing their data.

While the loading spinner is displayed, I would call my service function to retrieve the updated data. Once that is ready, I would update the DOM and hide the loading spinner.


#5

@DaDanny well , what i was thinking just to make sure the user data will be available before the view is showing specially if these data are images , working on media apps is suck "sorry for this " but this is what i feel. i need to re-implement using your way if i cannot find better at least for what i have now.


#6

That’s a great UX consideration but one other thing to consider:

If you wait for the resolve to complete before you transition to the view, what happens if you have a slow or no internet? The app would appear to freeze and the user couldn’t do anything.

I think I originally tried the resolve solution but I found it made the app appear much slower.

So what I always do is transition to the view, let the user know its loading and then update it. That way the app still seems responsive and they will think the problem is with their slow internet connection not the app.

Another solution/idea for you. What about setting up a timer while the user uses the app. This timer can start once the app is launched and every 30 seconds or whatever, it will fetch the latest data and store that in the service.

So whenever a user navigates between views, it will always appear refreshed and be the latest data from 30 seconds ago.


#7

@DaDanny sorry for being late to reply , i prefer using timer it is useful and this way i keep the user updated , i will keep looking for way to use resolved values and rebuild DOM variable.many thank Danny for sharing and helping .


#8

@DaDanny , i found this solution and you may be interested to know ,

<a ui-sref="profile" ui-sref-opts="{reload: true, inherit: false}">

    // <!-- OR with params -->

     <a ui-sref="profile({id: user.id})" ui-sref-opts="{reload: true, inherit: false}">

source : [How To Reload The Current State In Ionic 1.x App](https://solidfoundationwebdev.com/blog/posts/how-to-reload-the-current-state-in-ionic-1-x-app)

#9

@DaDanny
this is the most appropriate solution that is works for me , you do not need to disable cache , just clear cache when needed and you know data changed as below

$ionicHistory.clearCache().then(function(){ $state.go('tab.profile') })