EDIT: forgot to mention that i've been working with AngularJs for a week only, so if you see something you think should be changed for the better and is not related to the question itself feel free to tell me on the comments section.
ok, so I have my authentication Controllers and providers which I won't show because they're irrelevant for the scope of the question.
Then I have an interceptor to check if the user is authenticated when a Call is made. If so I set the Authentication header on the request to include the user's Token if not I redirect the user to the login page and don't even make the request to the server (obviously if someone bypasses this theres also an Authorize on the API).
What I want is to add a few exceptions, meaning there are some pages I want to allow even if the user has no Auth Token. I'm able to this if it's a specific path, but I want to allow my 404 page to be accessed and it's in the Routing that I'm specifying .otherwise to go to the 404 page, how can I make so that my interceptor only redirects to login if it's not going to this page.
The interceptor
.factory('authInterceptorService', ['$q', '$location', 'localStorageService', function ($q, $location, localStorageService) {
var authInterceptorServiceFactory = {};
var authData = localStorageService.get('authorizationData');
var _request = function (config) {
config.headers = config.headers || {};
if (authData) {
config.headers.Authorization = 'Bearer ' + authData.token;
} else if ($location.path != '/accounts/login' && $location.path != '/accounts/register') {
$location.path('/accounts/login');
}
return config;
}
var _responseError = function (rejection) {
if (rejection.status === 401) {
$location.path('/accounts/login');
}
return $q.reject(rejection);
}
authInterceptorServiceFactory.request = _request;
authInterceptorServiceFactory.responseError = _responseError;
return authInterceptorServiceFactory;
}])
and in my Routing
$urlRouterProvider.otherwise('/page-not-found');
$stateProvider
(...)//rest of the states
.state('page-not-found', {
url: '/page-not-found',
templateUrl: '/Content/partials/error/404.html',
data: {
displayName: false
}
})
(...)//rest of the states
I tried to add '/page-not-found' to my if but it won't work as expected because by the time the location is checked for the first time it's still not redirected.
edit As sugested by charlietfl I'm now trying to use resolve but it's not even passing my function.
I removed this code from my interceptor:
else if ($location.path != '/accounts/login' && $location.path != '/accounts/register') {
$location.path('/accounts/login');
}
and add a new service to the authentication module:
.service('authCheckService', ['$http', '$q', 'localStorageService', function ($http, $q, localStorageService) {
var self = {
'onlyLoggedIn': function ($state, $q) {
var deferred = $q.defer();
var authData = localStorageService.get('authorizationData');
console.log(authData);
if (authData) {
deferred.resolve();
} else {
deferred.reject();
$state.go('login');
}
return deferred.promise;
}
}
return self;
}]);
and i'm trying to call it as:
.state('smo-dashboard', {
url: '/dashboard',
templateUrl: '/Content/partials/dashboard.html',
resolve: authCheckServiceProvider.onlyLoggedIn
})
notice that i'm trying to log authData var to check if it's working but it isn't and there's no error on the console also.
resolveon that parent and if user not logged in all children of that state are inaccessible because parent won't resolve. for all other routes there would be nothing to checkresolveas suggested but I might be doing something wrong, can you please take a look at my edit