Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save definitelynotsoftware/e67e5cbe3e9943ecbb03 to your computer and use it in GitHub Desktop.
Save definitelynotsoftware/e67e5cbe3e9943ecbb03 to your computer and use it in GitHub Desktop.
AngularJS Windows Authentication Service using .NET Web API and Hot Towel template
angular.module('app')
.factory("authentication", ["$http", "$q", "$window", authentication]);
function authentication($http, $q, $window) {
var user;
function login() {
// check if the user already exists for this session
if (user) {
return $q.when(user); // resolve with given value, necessary because calling function expects a promise.
}
var url = 'api/users/current/';
return $http.get(url).then(function (result) {
var result = result.data;
user = {
id: result.UserId,
displayName: result.DisplayName,
guid: result.ADGuid,
isAdmin: result.IsAdmin
};
addUserToStorage();
console.log("user created.");
return $q.when(user);
});
}
function addUserToStorage() {
$window.sessionStorage["user"] = JSON.stringify(user);
}
function getUser() {
return user;
}
function init() {
if ($window.sessionStorage["user"]) {
user = JSON.parse($window.sessionStorage["user"]);
}
}
init();
return {
user: user,
init: init,
addUserToStorage: addUserToStorage,
login: login,
getUser: getUser
};
};
(function () {
'use strict';
var controllerId = 'base';
angular.module('app')
.controller(controllerId, ['common', 'authentication', base]);
function base(common, authentication) {
var vm = this;
// local vm.user object for use with topnav.html to display logged in user name
vm.user = { displayName: "..." };
activate();
function activate() {
common.activateController([login()], controllerId);
}
function login() {
return authentication.login().then(function (data) {
vm.user = data;
});
}
}
})();
// in the controllers, we can get the current user by deferring to authentication service
(function () {
'use strict';
var controllerId = 'sales';
angular.module('app')
.controller(controllerId, ['$q', 'common', 'authentication', sales]);
function sales($q, common, authentication)
{
// ...
// each controller has a call to getUser(), which defers to the authentication service for auth status
var vm = this;
vm.user = {};
activate();
function activate() {
// call the getUser promise
common.activateController([getUser()], controllerId)
.then(function () { });
}
function getUser() {
return authentication.login().then(function(data) {
vm.user = data;
return $q.when(data);
});
}
// ...
}
})();
<nav class="navbar navbar-fixed-top navbar-inverse">
<div class="navbar-header">
<a href="/" class="navbar-brand">
<span class="brand-title">
...
</span>
</a>
<a class="btn navbar-btn navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
</div>
<div class="navbar-collapse collapse" >
<div class="pull-right navbar-logo" data-ng-controller="base as vm">
<ul class="nav navbar-nav pull-right">
<li>
<a href="\">
Welcome, {{ vm.user.displayName }}
</a>
</li>
<li>
<a href="\">
</a>
</li>
<li class="dropdown dropdown-big">
<a href="http://localhost:20293/Help" target="_blank">Help</a>
</li>
</ul>
</div>
</div>
</nav>
public class User
{
public int UserId { get; set; }
public string DisplayName { get; set; }
public string ADGuid { get; set; }
public bool IsAdmin { get; set; }
}
public class UserFactory
{
private readonly IQwDbContext db = new QwDbContext();
public User Create(WindowsIdentity currentWindowsUser)
{
var user = new User();
string name = currentWindowsUser.Name.Replace("DOMAIN\\", "");
// a much simplified case for example (better to retrieve by GUID)
User userInDatabase = (from u in db.Users
where u.FirstName.ToLower() + u.LastName.ToLower() == name.ToLower()
select u).FirstOrDefault();
if (userInDatabase != null)
{
user.UserId = userInDatabase.UserId;
user.DisplayName = userInDatabase.DisplayName;
user.IsAdmin = userInDatabase.IsAdmin;
user.ADGuid = userInDatabase.ADGuid;
}
return user;
}
}
[RoutePrefix("api/users")]
public class UsersController : ApiController
{
/// <summary>
/// Gets the currently logged in user account in AD as a User object
/// </summary>
/// <returns></returns>
[Route("current/")]
public User GetCurrentUser()
{
User user = new UserFactory().Create(WindowsIdentity.GetCurrent());
return user;
}
}
@shkup
Copy link

shkup commented Dec 7, 2015

Shouldn't you use interceptor service for authentication?

@tobiashoeft
Copy link

Nice and clear explanation. I implemented and ran locally it works as expected. But when I deploy to IIS as two separate website ( WebAPI and AngularJS ) , now I get identity as IIS hosted account and not the User account.
Can you give me hint how can I achieve the same on deployment.

The same here , how can i use that for Production

@mgonzales3
Copy link

after looking at node-activedirectory and ldapjs this is probably the best solution. otherwise go back to asp.net mvc stack.

@VCS-Deepak
Copy link

type or namespace name DbContext could not be found

@davidjefferson
Copy link

davidjefferson commented May 16, 2017

What is this common? My angular always returns Unknown provider: commonProvider <- common.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment