发生什么是模板被渲染,一些ajax调用资源发生,然后我们被重定向到rails devise登录。我宁愿做一个ping到每个状态更改的rails,如果rails会话已过期,我将立即重定向之前的模板呈现。@H_404_2@
ui路由器有解决方案,可以放在每个路由,但似乎不是干的。@H_404_2@
我有这个。但是,在国家已经过渡之前,承诺才能解决。@H_404_2@
$rootScope.$on('$stateChangeStart',function(event,toState,toParams,fromState,fromParams){ //check that user is logged in $http.get('/api/ping').success(function(data){ if (data.signed_in) { $scope.signedIn = true; } else { window.location.href = '/rails/devise/login_path' } }) });
如何在呈现新模板之前基于promise的结果中断状态转换?@H_404_2@
例如:@H_404_2@
$rootScope.$on('$stateChangeStart',function (event,toParams) { toState.resolve.promise = [ '$q',function($q) { var defer = $q.defer(); $http.makeSomeAPICallOrWhatever().then(function (resp) { if(resp = thisOrThat) { doSomeThingsHere(); defer.resolve(); } else { doOtherThingsHere(); defer.resolve(); } }); return defer.promise; } ] });
这将确保状态更改保持要解决的承诺,当API调用完成并且基于从API返回的所有决定时,该承诺被完成。我使用它来检查服务器端的登录状态,然后才允许导航新页面。当API调用解析时,我使用“event.preventDefault()”停止原始导航,然后路由到登录页面(用if state.name!=“login”围绕整个代码块)或允许用户继续通过简单地解决延迟的承诺,而不是试图使用旁路布尔和preventDefault()。@H_404_2@
虽然我确信原来的海报很久以来就找出了他们的问题,我真的希望这有助于别人在那里。@H_404_2@
编辑@H_404_2@
我想我不想误导人。如果你不确定你的状态是否有解析对象,代码应该是什么样子:@H_404_2@
$rootScope.$on('$stateChangeStart',toParams) { if (!toState.resolve) { toState.resolve = {} }; toState.resolve.pauseStateChange = [ '$q',function($q) { var defer = $q.defer(); $http.makeSomeAPICallOrWhatever().then(function (resp) { if(resp = thisOrThat) { doSomeThingsHere(); defer.resolve(); } else { doOtherThingsHere(); defer.resolve(); } }); return defer.promise; } ] });
编辑2@H_404_2@
为了得到这个工作对于没有解决定义的状态,你需要在app.config中添加:@H_404_2@
var $delegate = $stateProvider.state; $stateProvider.state = function(name,definition) { if (!definition.resolve) { definition.resolve = {}; } return $delegate.apply(this,arguments); };
做if(!toState.resolve){toState.resolve = {}};在stateChangeStart似乎不工作,我认为ui路由器不接受解决dict后,它已经初始化。@H_404_2@