angularjs localStorageServiceProvider - angularjs

I am trying to follow this tutorial
http://www.codeproject.com/Articles/784106/AngularJS-Token-Authentication-using-ASP-NET-Web-A
I don't know which angularjs package to download so that I could use localStorageService and ngAuthSettings in my angularjs code.
I am getting the following err when I run the mvc 5 asp.net vs2013 web api app.
Unknown provider: localStorageServiceProvider <- localStorageService <- authInterceptorService <- $http <- $templateRequest <- $compile
Here is my code.
var appointmentReminderApp = angular.module('appointmentReminderApp', ["ngRoute", "ui.bootstrap"]);
appointmentReminderApp.config(function ($routeProvider, $locationProvider,$httpProvider) {
$httpProvider.interceptors.push('authInterceptorService');
$locationProvider.html5Mode(true);
$routeProvider
.when("/home", {
templateUrl: "App/Home.html",
controller: "HomeController"
})
.when("/Register", {
templateUrl: "App/AuthForm/templates/register.html",
controller: "authRegisterController"
})
.when("/Login", {
templateUrl: "App/AuthForm/templates/login.html",
controller: "authLoginController"
})
.otherwise({ redirectTo: "/home" });
});
appointmentReminderApp.factory('authInterceptorService', ['$q', '$injector', '$location', 'localStorageService', function ($q, $injector, $location, localStorageService) {
var authInterceptorServiceFactory = {};
var _request = function (config) {
config.headers = config.headers || {};
var authData = localStorageService.get('authorizationData');
if (authData) {
config.headers.Authorization = 'Bearer ' + authData.token;
}
return config;
}
var _responseError = function (rejection) {
if (rejection.status === 401) {
var authService = $injector.get('authService');
var authData = localStorageService.get('authorizationData');
if (authData) {
if (authData.useRefreshTokens) {
$location.path('/refresh');
return $q.reject(rejection);
}
}
authService.logOut();
$location.path('/login');
}
return $q.reject(rejection);
}
authInterceptorServiceFactory.request = _request;
authInterceptorServiceFactory.responseError = _responseError;
return authInterceptorServiceFactory;
}]);
appointmentReminderApp.factory('authService', ['$http', '$q', 'localStorageService', 'ngAuthSettings', function ($http, $q, localStorageService, ngAuthSettings) {
var registerUser = function (auth) {
return $http.post("/api/Account/Register", auth);
};
var loginUser = function (loginData) {
var data = "grant_type=password&username=" + loginData.userName + "&password=" + loginData.Password;
if (loginData.useRefreshTokens) {
data = data + "&client_id=" + ngAuthSettings.clientId;
}
var deferred = $q.defer();
$http.post(serviceBase + 'token', data, { headers: { 'Content-Type': 'application/x-www-form-urlencoded' } }).success(function (response) {
if (loginData.useRefreshTokens) {
localStorageService.set('authorizationData', { token: response.access_token, userName: loginData.userName, refreshToken: response.refresh_token, useRefreshTokens: true });
}
else {
localStorageService.set('authorizationData', { token: response.access_token, userName: loginData.userName, refreshToken: "", useRefreshTokens: false });
}
_authentication.isAuth = true;
_authentication.userName = loginData.userName;
_authentication.useRefreshTokens = loginData.useRefreshTokens;
deferred.resolve(response);
}).error(function (err, status) {
_logOut();
deferred.reject(err);
});
return deferred.promise;
};
return {
registerUser: registerUser,
loginUser: loginUser
};
}
]);

Have you downloaded the angular local storage service module? do you have this line
<script src="scripts/angular-local-storage.min.js"></script>
in your index.html?

The required JS file doen't come bundled with Angular.
You can get it from here.
I was unable to find the CDN, will update if I find one.

Related

separated controller from component

Component:
crudModule.js
var crudModule = angular.module('crudModule', ['ui.router', 'smart-table', 'ngCookies', 'ui.bootstrap', 'angularModalService', 'dialogs', 'remoteValidation']);
angular.module('crudModule').component('applicationInfo', {
templateUrl: 'infoApplication.html',
controller: 'applicationInfoCtrl'
});
applicationInfoCtrl.js:
var crudModule = angular.module('crudModule')
crudModule.controller('applicationInfoCtrl', ['httpService', '$scope', function($http, $scope, $cookies, $stateParams, httpService) {
httpService.httpGetRequest("http://localhost:8080/applications/" + $stateParams.id).then(function success(response) {
$scope.application = response.data;
});
$scope.getApiKey = function () {
httpService.httpGetRequest('http://localhost:8080/applications/generateApiKey').then(function success(response) {
$scope.application.apikey = response.data.apikey;
$scope.application.apisecret = response.data.apisecret
})
};
$scope.send = function (object, url) {
httpService.httpPostRequest(object, url + "/" + $stateParams.id).catch(function(error) {
console.log('There has been a problem with your fetch operation: ' + error.message);
}).then(function success(response){
});
}
}]);
httpService.js:
var crudModule = angular.module('crudModule')
crudModule.factory('httpService', function($http) {
return {
httpGetRequest: function (url) {
return $http({
method: 'GET',
url: url
})
},
httpPostRequest: function (object, url){
return $http({
method:'POST',
url: url,
data: object
})
}
}
});
I am getting error:
Cannot read property 'httpGetRequest' of undefined.
I have injected my httpService and i dont find any mistakes yet
The problem is the order of parameters in your controller, it should be
crudModule.controller('applicationInfoCtrl', ['$http','httpService', '$scope','$cookies','$stateParams' function(http,httpService, $scope,$cookies,$stateParams) {
}

"unsupported_grant_type" error in angular user Authentication with $resource

My Issue
Everything working fine with $post but when I update it to $resource,
I am getting error of unsupported_grant_type.
I tried many solutions from SO, but unable to resolve this issue.
Below is my code.
Controller
$scope.login = function () {
authService.login($scope.loginData).promise.then(function (response) {
if (document.referrer != "" && document.referrer != window.location.href) {
window.location.href = document.referrer;
}
else {
window.location.href = "/Roles/Index"
}
}
};
Service
app.factory('authService', ['$http', '$q', 'localStorageService', '$resource', '$rootScope',
function ($http, $q, localStorageService, $resource, $rootScope) {
var authServiceFactory = {};
var _authentication = {
isAuth: false,
userName: ""
};
var url = function (relativeUrl) {
return $rootScope.apiBaseUrl + '/api/' + relativeUrl;
};
var authResource = $resource(url('account/:id'), null, {
register: {
method: 'POST',
url: url('account/register')
},
login: {
method: 'POST',
url: $rootScope.apiBaseUrl + '/token'
}
},
{
headers: {
'Access-Control-Allow-Origin': '*',
'Content-Type': 'application/x-www-form-urlencoded'
}
});
var _login = function (loginData) {
// var data = "grant_type=password&username=" + loginData.userName + "&password=" + loginData.password;
loginData.grant_type = "password";
var deferred = $q.defer();
authResource.login($.param(loginData)).$promise
.then(function (response) {
localStorageService.set('authorizationData', { token: response.access_token, userName: loginData.userName });
_authentication.isAuth = true;
_authentication.userName = loginData.userName;
deferred.resolve(response);
});
return deferred;
};
var _fillAuthData = function () {
var authData = localStorageService.get('authorizationData');
if (authData) {
_authentication.isAuth = true;
_authentication.userName = authData.userName;
}
}
authServiceFactory.saveRegistration = _saveRegistration;
authServiceFactory.login = _login;
authServiceFactory.logOut = _logOut;
authServiceFactory.fillAuthData = _fillAuthData;
authServiceFactory.authentication = _authentication;
return authServiceFactory;
}]);
What I found from so many tries?
I found that, My request does not have any headers.

Send ClientID and Secret in Authorization header ( angularjs )

I am building a simple Client App which is talking to a rest api and getting information about the user. I am implementing Resource Owner Password Credentials Flow of OAuth.
I have been struggling with how to send my client ID and Secret in Authorization header in an angular app.
I have built an authService and an interceptor service to handle my login.
my app.js
'use strict';
var app = angular.module('AngularAuthApp', ['ngRoute', 'LocalStorageModule', 'angular-loading-bar']);
app.config(function ($routeProvider) {
$routeProvider.when("/home", {
controller: "homeController",
templateUrl: "/views/home.html"
});
$routeProvider.when("/login", {
controller: "loginController",
templateUrl: "/views/login.html"
});
$routeProvider.otherwise({ redirectTo: "/home" });
});
app.run(['authService', function (authService) {
authService.fillAuthData();
}]);
app.config(function ($httpProvider) {
$httpProvider.interceptors.push('authInterceptorService');
});
this is my authService.js
app.factory('authService', ['$http', '$q', 'localStorageService', function ($http, $q, localStorageService) {
var serviceBase = 'http://url/oauth/';
var authServiceFactory = {};
var _authentication = {
isAuth: false,
userName : ""
};
var _login = function (loginData) {
var data = "grant_type=password&username=" + loginData.userName + "&password=" + loginData.password ;
var deferred = $q.defer();
$http.post(serviceBase + 'token', data, { headers: { 'Content-Type': 'application/x-www-form-urlencoded' } }).success(function (response) {
localStorageService.set('authorizationData', { token: response.access_token, userName: loginData.userName });
_authentication.isAuth = true;
_authentication.userName = loginData.userName;
deferred.resolve(response);
}).error(function (err, status) {
_logOut();
deferred.reject(err);
});
return deferred.promise;
};
authServiceFactory.login = _login;
return authServiceFactory;
}]);
and authInterceptorService.js
app.factory('authInterceptorService', ['$q', '$location', 'localStorageService', function ($q, $location, localStorageService) {
var authInterceptorServiceFactory = {};
var _request = function (config) {
config.headers = config.headers || {};
var authData = localStorageService.get('authorizationData');
if (authData) {
config.headers.Authorization = 'Bearer ' + authData.token;
}
return config;
}
var _responseError = function (rejection) {
if (rejection.status === 401) {
$location.path('/login');
}
return $q.reject(rejection);
}
authInterceptorServiceFactory.request = _request;
authInterceptorServiceFactory.responseError = _responseError;
return authInterceptorServiceFactory;
}]);
My curl request which throws me an access token is
curl -X POST -vu sampleapp:samplekey http://sampleurl/oauth/token -H "Accept: application/json" -d "password=pwd&username=uname&grant_type=password&scope=read%20write&client_secret=samplekey&client_id=sampleapp"
So, I am guessing that I need to send the clientID and clientSecret but am not sure how to implement it or where to add it. I have looked into documents saying that we might need to add to authorization header but I don't think I'm doing it right. Also, do I need to encode it or anything ? This is not a JWT token but a simple token. Do I also need to send in the scope ?
I am getting a 401 error of Full authentication is required to access this resource as of now.

AngularJS defer return until completed

I have tried to build a service that will return a $resource after the service has authenticated.
I have done it like this:
.factory('MoltinApi', ['$q', '$resource', '$http', 'moltin_options', 'moltin_auth', function ($q, $resource, $http, options, authData) {
var api = $resource(options.url + options.version + '/:path', {
path: '#path'
});
var authenticate = function () {
if (!options.publicKey)
return;
var deferred = $q.defer();
var request = {
method: 'POST',
url: options.url + 'oauth/access_token',
headers: {
'Content-Type': 'application/x-www-form-urlencoded'
},
data: "grant_type=implicit&client_id=" + options.publicKey
};
$http(request).success(function (response) {
authData = response;
deferred.resolve(api);
});
return deferred.promise;
};
return authenticate();
}])
But I can not call the resource in my controller:
.controller('HomeController', ['MoltinApi', function (moltin) {
var self = this;
moltin.get({ path: 'categories' }, function (categories) {
console.log(categories);
});
}]);
it just states that 'undefined is not a function'.
Can someone tell me what I am doing wrong?
Update 1
So after playing with the solution that was suggested, this is the outcome.
angular.module('moltin', ['ngCookies'])
// ---
// SERVICES.
// ---
.factory('MoltinApi', ['$cookies', '$q', '$resource', '$http', 'moltin_options', function ($cookies, $q, $resource, $http, options) {
var api = $resource(options.url + options.version + '/:path', {
path: '#path'
});
var authenticate = function () {
if (!options.publicKey)
return;
var deferred = $q.defer();
var authData = angular.fromJson($cookies.authData);
if (!authData) {
console.log('from api');
var request = {
method: 'POST',
url: options.url + 'oauth/access_token',
headers: {
'Content-Type': 'application/x-www-form-urlencoded'
},
data: "grant_type=implicit&client_id=" + options.publicKey
};
deferred.resolve($http(request).success(function (response) {
$cookies.authData = angular.toJson(response);
setHeaders(response.access_token);
}));
} else {
console.log('from cookie');
deferred.resolve(setHeaders(authData.access_token));
}
return deferred.promise;
};
var setHeaders = function (token) {
$http.defaults.headers.common['Authorization'] = 'Bearer ' + token;
}
return authenticate().then(function (response) {
return api;
});
}]);
and to call it I have to do this:
.controller('HomeController', ['MoltinApi', function (moltin) {
var self = this;
moltin.then(function (api) {
api.get({ path: 'categories' }, function (categories) {
console.log(categories);
self.sports = categories.result;
});
});
}]);
but what I would like to do is this:
.controller('HomeController', ['MoltinApi', function (moltin) {
var self = this;
moltin.get({ path: 'categories' }, function (categories) {
console.log(categories);
}, function (error) {
console.log(error);
});
}]);
As you can see, the service is checking to see if we have authenticated before returning the API. Once it has authenticated then the API is returned and the user can then call the api without having to authenticate again.
Can someone help me refactor this service so I can call it without having to moltin.then()?
You are returning the authenticate function call in the MoltinApi factory, so you are returning the promise. And the method get doesn't exist in the promise

Angularjs $on not firing after $rootScope.$broadcast

I have this code where two controllers are using a shared service to communicate.
var app = angular.module('AdminApp', ['ngRoute']);
app.factory('SharedService', function ($rootScope) {
var sharedService = {
userId: [],
BroadcastUserId: function (id) {
this.userId.push(id);
$rootScope.$broadcast('handleBroadcast');
}
};
return sharedService;
});
app.config(function ($routeProvider) {
$routeProvider.when('/login', {
templateUrl: "adminLogin.html"
});
$routeProvider.when('/main', {
templateUrl: 'adminMain.html'
});
$routeProvider.otherwise({
redirectTo: '/login'
});
});
app.controller('authCtrl', function ($scope, $http, $location, SharedService) {
$scope.Userid = '';
$scope.authenticate = function (user, pass) {
$http.post('http://localhost/NancyAPI/auth', {
UserName: user,
Password: pass
}).success(function (data) {
$scope.$broadcast('Token', data.Token);
$http.defaults.headers.common['Authorization'] = 'Token ' + data.Token;
$scope.Userid = data.UserId;
SharedService.BroadcastUserId($scope.Userid);
$location.path("/main");
}).error(function (response) {
$scope.authenticationError = response.error || response;
});
};
$scope.$on('handleBroadcast', function () {
console.log('on');
});
}).$inject = ['$scope', '$rootScope', 'SharedService'];
app.controller('mainCtrl', function ($scope, $http, $q, SharedService) {
$scope.tests = [];
$scope.userId = -1;
$scope.getTests = function () {
var deferred = $q.defer();
$http.get('http://localhost/NancyAPI/auth/tests/' + $scope.userId).
success(function (data) {
deferred.resolve(data);
$scope.tests = angular.fromJson(data);
}).error(function (response) {
});
};
// THIS IS NOT FIRING
$scope.$on('handleBroadcast', function () {
$scope.userId = SharedService.userId;
});
}).$inject = ['$scope', '$rootScope', 'SharedService'];
For some reason the $scope.$on is firing in the AuthCtrl controller but not in the mainCtrl.
// THIS IS NOT FIRING
$scope.$on('handleBroadcast', function () {
$scope.userId = SharedService.userId;
});
Why is this happening and how do I fix it?
I made a subtle mistake of not providing the {$rootScope} as dependency. Once I corrected that, it worked for me. I used Inline Array Annotation mechanism to achieve the same.

Resources