Próbuję zaimplementować system sprawdzania autentyczności użytkownika i systemu kontroli dostępu w mojej aplikacji, ale nadal trafiam na blokady dróg. Myślę, że tym razem mam to we właściwy sposób, ale mam ostatnią przeszkodę.
Nieco tła: próbowałem umieścić cały kod w $ rootScope.on ($ startChangeStart) i zadziałało, strasznie ... ale zadziałało. Trasa zawsze była przekierowywana, ale z powodu auth sprawdzenia w backendach wyświetlała pierwszą stronę żądania przez 1/2 sekundy, a następnie za każdym razem stronę przekierowania. Próbowałem więc wstrzymać ładowanie strony, wywołując funkcję evt.preventDefault() na samym początku funkcji $ startChangeStart, która działała, ale próba przeniesienia użytkownika na pierwotną trasę spowodowała nieskończoną pętlę w routerze.
Po więcej badań i przeczytaniu wielu postów na stosach jestem pewien, że "postanowienie:" jest właściwym miejscem do sprawdzenia auth, aby upewnić się, że strona nie ładuje się podczas jej występowania, a następnie przekierować użytkownika, jeśli potrzebne od $ startChangeStart. (Stan i wydarzenie $ są zawsze niezdefiniowane w moich próbach wprowadzenia ich do funkcji rozstrzygania). Wygląda to na zwycięską kombinację.
Mój problem: Mam postanowienie w sprawie stanu głównego w moim app: „main”
To było uniknąć redundancji kodu, jednak nie mogę określić, w jaki sposób uzyskać dostęp do właściwości Państwowej root, a zatem wynik resolve , z $ stateChangeStart. ToState jest stanem podrzędnym, podczas gdy parametr fromState jest stanem poprzednim lub stanem abstrakcyjnym z trasą "^" ...
Czy muszę rozwiązać każdy stan dziecka, aby to zadziałało, lub czy istnieje sposób na uzyskanie dostępu do stanu root z tego punktu?
Podstawowa aplikacja setup:
angular.module('App', ['ui.router', 'ui.bootstrap', 'ui.event', 'AngularGM', 'ngResource'])
.config(['$urlRouterProvider', '$stateProvider', function($urlRouterProvider, $stateProvider){
$urlRouterProvider
.when('/home', '/')
.when('', '/')
.when('/sign-up/joe', '/sign-up')
.otherwise('/');
$stateProvider
.state('main', {
url: '',
abstract: true,
templateUrl: 'views/main.html',
controller: 'MainCtrl',
resolve: {
checkAccess: ['accountService', function(accountService) {
accountService.checkAuth(function(){
accountService.checkAccess(function (access){
return access;
});
});
}]
}
})
.state('main.home', {
url: '',
abstract: true,
templateUrl: 'views/home.html',
controller: 'HomeCtrl'
})
.state('main.home.index', {
url: '/',
templateUrl: 'views/home/index.html'
});
.run(['$rootScope', '$state', '$stateParams', 'accountService', function ($rootScope, $state, $stateParams) {
$rootScope.$state = $state;
$rootScope.$stateParams = $stateParams;
$rootScope.$on('$stateChangeStart', function(event, toState, toParams, fromState, fromParams) {
console.dir(toState);
console.dir(toParams);
console.dir(fromState);
console.dir(fromParams);
if (!toState.checkAccess.allowed) {
event.preventDefault();
$state.transitionTo(toState.checkAccess.newState);
}
});
}]);
Jest to wyjście z console.dir() zwraca się z dwóch obiektów państwowych:
Object
name: "main.home.index"
templateUrl: "views/home/index.html"
url: "/"
__proto__: Object
Object
controller: "PlacesCtrl"
name: "main.places.search"
templateUrl: "views/places.html"
url: "/places"
__proto__: Object
Aktualizacja
Ups, zapomniałem wspomnieć o wersji AngularJS v1.2.0-rc.2
$ state.current console.dir()
Object
abstract: true
name: ""
url: "^"
views: null
__proto__: Object
Po prostu zrobiłem plik console.dir na obiekcie $ state.current w $ stateChangeStart i został on teraz dodany. To abstrakcyjny obiekt. Jeśli przeniesię prace do innej funkcji i użyję stanu $ z wewnątrz, to stanem $ będzie obiekt podrzędny .. ale powinien istnieć sposób dostępu do niego bez tworzenia dodatkowych linii dla funkcji ... nie? Ponadto, to nadal nie daje mi dostępu do stanu root, który zawiera postanowienie. – Routhinator
Czy udało Ci się dowiedzieć, jak uzyskać dostęp do danych rozstrzygnięcia z poziomu stateChangeStart? – Yavar
Miałem wrażenie, że dane rozstrzygnięcia zostały "rozwiązane" po zdarzeniu stateChangeStart ... ie. jeśli wywołasz 'event.preventDefault()', wynik nigdy się nie rozpocznie. Może się mylę. –