Reloading current state - refresh data

2018-12-31 23:07发布

问题:

I\'m using Angular UI Router and would like to reload the current state and refresh all data / re-run the controllers for the current state and it\'s parent.

I have 3 state levels: directory.organisations.details

directory.organisations contains a table with a list of organisations. Clicking on an item in the table loads directory.organisations.details with $StateParams passing the ID of the item. So in the details state I load the details for this item, edit them and then save data. All fine so far.

Now I need to reload this state and refresh all the data.

I have tried:

 $state.transitionTo(\'directory.organisations\');

Which goes to the parent state but doesn\'t reload the controller, I guess because the path hasn\'t changed. Ideally I just want to stay in the directory.organisations.details state and refresh all data in the parent too.

I have also tried:

$state.reload()

I have seen this on the API WIKI for $state.reload \"(bug with controllers reinstantiating right now, fixing soon).\"

Any help would be appreciated?

回答1:

I found this to be the shortest working way to refresh with ui-router:

$state.go($state.current, {}, {reload: true}); //second parameter is for $stateParams

Update for newer versions:

$state.reload();

Which is an alias for:

$state.transitionTo($state.current, $stateParams, { 
  reload: true, inherit: false, notify: true
});

Documentation: https://angular-ui.github.io/ui-router/site/#/api/ui.router.state.$state#methods_reload



回答2:

This solution works in AngularJS V.1.2.2:

$state.transitionTo($state.current, $stateParams, {
    reload: true,
    inherit: false,
    notify: true
});


回答3:

That would be the final solution. (inspired by @Hollan_Risley\'s post)

\'use strict\';

angular.module(\'app\')

.config(function($provide) {
    $provide.decorator(\'$state\', function($delegate, $stateParams) {
        $delegate.forceReload = function() {
            return $delegate.go($delegate.current, $stateParams, {
                reload: true,
                inherit: false,
                notify: true
            });
        };
        return $delegate;
    });
});

Now, whenever you need to reload, simply call:

$state.forceReload();


回答4:

for ionic framework

$state.transitionTo($state.current, $state.$current.params, { reload: true, inherit: true, notify: true });//reload

$stateProvider.
  state(\'home\', {
    url: \'/\',
    cache: false, //required

https://github.com/angular-ui/ui-router/issues/582



回答5:

Probably the cleaner approach would be the following :

<a data-ui-sref=\"directory.organisations.details\" data-ui-sref-opts=\"{reload: true}\">Details State</a>

We can reload the state from the HTML only.



回答6:

@Holland Risley \'s answer is now available as an api in latest ui-router.

$state.reload();

A method that force reloads the current state. All resolves are re-resolved, controllers reinstantiated, and events re-fired.

http://angular-ui.github.io/ui-router/site/#/api/ui.router.state.$state



回答7:

$state.go($state.current, $stateParams, {reload: true, inherit: false});


回答8:

$scope.reloadstat = function () { $state.go($state.current, {}, {reload: true}); };


回答9:

if you want to reload your entire page, like it seems, just inject $window into your controller and then call

$window.location.href = \'/\';

but if you only want to reload your current view, inject $scope, $state and $stateParams (the latter just in case you need to have some parameters change in this upcoming reload, something like your page number), then call this within any controller method:

$stateParams.page = 1;
$state.reload();

AngularJS v1.3.15 angular-ui-router v0.2.15



回答10:

Silly workaround that always works.

$state.go(\"otherState\").then(function(){
     $state.go(\"wantedState\")
});


回答11:

For angular v1.2.26, none of the above works. An ng-click that calls the above methods will have to be clicked twice in order to make the state reload.

So I ended up emulating 2 clicks using $timeout.

$provide.decorator(\'$state\',
        [\"$delegate\", \"$stateParams\", \'$timeout\', function ($delegate, $stateParams, $timeout) {
            $delegate.forceReload = function () {
                var reload = function () {
                    $delegate.transitionTo($delegate.current, angular.copy($stateParams), {
                        reload: true,
                        inherit: true,
                        notify: true
                    })
                };
                reload();
                $timeout(reload, 100);
            };
            return $delegate;
        }]);


回答12:

Everything failed for me. Only thing that worked...is adding cache-view=\"false\" into the view which I want to reload when going to it.

from this issue https://github.com/angular-ui/ui-router/issues/582



回答13:

Not sure why none of these seemed to work for me; the one that finally did it was:

$state.reload($state.current.name);

This was with Angular 1.4.0



回答14:

I had multiple nested views and the goal was to reload only one with content. I tried different approaches but the only thing that worked for me is:

//to reload
$stateParams.reload = !$stateParams.reload; //flip value of reload param
$state.go($state.current, $stateParams);

//state config
$stateProvider
  .state(\'app.dashboard\', {
    url: \'/\',
    templateUrl: \'app/components/dashboard/dashboard.tmpl.html\',
    controller: \'DashboardController\',
    controllerAs: \'vm\',
    params: {reload: false} //add reload param to a view you want to reload
  });

In this case only needed view would be reloaded and caching would still work.



回答15:

I know there have been a bunch of answers but the best way I have found to do this without causing a full page refresh is to create a dummy parameter on the route that I want to refresh and then when I call the route I pass in a random number to the dummy paramter.

            .state(\"coverage.check.response\", {
                params: { coverageResponse: null, coverageResponseId: 0, updater: 1 },
                views: {
                    \"coverageResponse\": {
                        templateUrl: \"/Scripts/app/coverage/templates/coverageResponse.html\",
                        controller: \"coverageResponseController\",
                        controllerAs: \"vm\"
                    }
                }
            })

and then the call to that route

$state.go(\"coverage.check.response\", { coverageResponse: coverage, updater: Math.floor(Math.random() * 100000) + 1 });

Works like a charm and handles the resolves.



回答16:

You can use @Rohan answer https://stackoverflow.com/a/23609343/3297761

But if you want to make each controller reaload after a view change you can use

myApp.config(function($ionicConfigProvider) { $ionicConfigProvider.views.maxCache(0); ... }


回答17:

I had this problem it was wrecking my head, my routing is read from a JSON file and then fed into a directive. I could click on a ui-state but I couldn\'t reload the page. So a collegue of mine showed me a nice little trick for it.

  1. Get your Data
  2. In your apps config create a loading state
  3. Save the state you want to go to in the rootscope.
  4. Set your location to \"/loading\" in your app.run
  5. In the loading controller resolve the routing promise and then set the location to your intended target.

This worked for me.

Hope it helps



回答18:

If you are using ionic v1, the above solution won\'t work since ionic has enabled template caching as part of $ionicConfigProvider.

Work around for that is a bit hacky - you have to set cache to 0 in ionic.angular.js file:

$ionicConfigProvider.views.maxCache(0);