Architecture Direction Help: Creating an Azure Active Directory PAM Module - azure

I'm interested in creating a Linux Pluggable Authentication Module (PAM) that authenticates against Azure Active Directory. It appears that Oauth 2.0 is what Microsoft uses for this.
In reviewing the Authentication Scenarios it seems that the "Daemon or Server Application" probably makes the most sense, but I'm not positive. "Native Application to Web API" might also be a possibility, but all the app flows given show kicking off a pop-up browser instance to authenticate, which doesn't seem possible in PAM. As a result, unless I'm scrapping responses that flow doesn't appear to work, and scrapping responses seems like a bad idea.
My questions:
What is the best way to validate a user's credentials for this scenario? Is a Daemon or Native App?
What is the rough flow I would be looking at to do this? (e.g. If I'm using a Daemon, what calls do I make to validate the user creds?)
Any idea on what this looks like if 2FA is enabled for a user?
Thank-you for your help. I feel like none of the available options really fit here, and want to make sure I'm heading the right direction until I invest a bunch of time in here.

bureado's PAM you point to uses what's known as the OAuth "Resource Owner Password Credentials Grant". It basically takes the user's username & password and passes them to Azure AD for authentication. It has a bunch of limitations, several of which Vittorio describes here. A core problem you pointed out is that MFA does not work.
For scenarios like this Azure AD also supports the OAuth "Device Profile Flow". There's a code sample here that shows how to do it in .NET: https://github.com/Azure-Samples/active-directory-dotnet-deviceprofile. I'd recommend going that route.

Okay, I found the following module that appears to mostly do what I'm looking to do anyway:
https://github.com/bureado/aad-login
He chose to use "Native App". I'm still not positive if this is the "best option" and therefore I'm going to leave this open to other answers. I'd love it if someone could explain why this is the best option.
Meanwhile, I'm now trying to get AAD group memberships to be imported in like pam_ldap, or pam_kerberos, but I'm having a hard time figuring out how that's supposed to work, and have posted another question:
How to write a PAM module which changes group membership?
Should anyone come across this later and want to do the same thing, we're planning on open sourcing the final modified solution with this extended functionality. It doesn't do it yet, but the code is on GitHub here:
https://github.com/CyberNinjas/aad-login

Related

OAuth scopes for different flows in same application?

Context
I have a Node.js application that has a "complex" set of OAuth flows in order to make the UX simpler.
I have the usual login and registration flow where you may use an OAuth provider to authenticate. I don't require any special scope here, since OAuth is being used purely for authentication and the user has no reason to want to give me elevated access (say to private GitHub repositories), and might even think this is a shady thing to ask, so he goes away and never visits my product again. So, no scope for the pure authentication flow.
The application also has an import functionality where you can import a list of entities from an OAuth provider (say, GitHub repositories). By default, you aren't asked for any scope here either.
Clicking on the "Looking for your private repositories?" button authenticates you against GitHub again, asking for the repo scope. This is all fine and well.
The issue
Is that when the user tries to login again, or otherwise do anything that might authenticate them but doesn't explicitly request the repo scope, GitHub deems this an explicit downgrade request.
The issue is the user wouldn't want to downgrade during logins for no particular reason. Similarly, I don't want to ask for more permissions than I need during logins.
Leaving things in this state would be even worse than asking for repo at login, but that would be an extremely poor choice as well.
Potential Solutions
Besides the two non-solutions, the potential solutions I've come up with are:
Ask GitHub explicitly for unique access tokens based on the requested scope, store the tokens separately, and use them as needed afterwards
That'd be great, except it'd be way too stateful and I haven't found a way to do it anyways; they seem to give you a single token per application user, and I suspect this is how OAuth works, for the most part, but I'm hardly an expert on the matter.
Tell GitHub explicitly not to downgrade a token if it has more priviledge than what it's asking for.
This sounds to me that it should be the default behavior. Anyways, is there any way I can tell GitHub not to downgrade a token?
If not, is there any other way I can fix this without resorting to asking for the same scope across the entire application? This would partially defeat the purpose of scopes in the first place.
Also, is this a GitHub-specific issue? Will I have to deal with this in a provider-by-provider basis? Is there a protocol-level solution that miraculously makes the problem go away? Or is OAuth just not built with UX in mind?
FWIW I'm using iojs and passportjs, but I don't think that has anything to do with the question.
Turns out the issue was in my code, as it usually goes. I was explicitly setting a property (options.scope: [], for those using passport) on the authentication flow, and that resulted in a GitHub authorization URL that contained &scope=&, meaning I was explicitly asking for a downgrade.
Removing the option in case I have no explicit scope to ask for fixed the issue. Woo!

Initial "No OpenID Endpoint Found" on Windows Azure

I've looked at the various questions on this topic but none of them QUITE fit the problem I'm having.
I've developed an MVC4 app which utilizes DNOA to call into a particular provider (Intuit). All worked perfectly on my local IIS (testing) but when I deployed to Windows Azure I get the proverbial wonderful "strange, intermittent" behavior. Specifically, 99% of the time, the initial sign-in request results in the "No OpenID Endpoint Found" error; however, SUBSEQUENT sign-ins go through without a hitch.
I've added the code referred to here: ServiceManagerCode, to no avail. I've checked and the OpenID URL is correct. I've also attempted to add log4net to see what might be occurring but have been unable to do this correctly, some other answers seem to suggest this returns nothing anyway. I've also asked Intuit but, so far, no responses.
Again, if this wasn't occurring on just the first attempt then there would be numerous relevant posts but with this peculiar behavior I am wary of wasting inordinate amounts of time on a wild goose chase.
Any suggestions, however slight, would be very much appreciated.
I am not familiar with OpenID. Is the OpenID sign in service hosted by you in Windows Azure as well? Please make sure the sign in service has started without any problems, one suggestion is to check the federation configuration. Most federation providers require you to configure the realm and return URL. If they’re not properly configured, the application won’t work.
Best Regards,
Ming Xu.
Since you say that your Azure relying party works reliably after the first failed attempt, perhaps you can workaround it by having your app_start event in your Azure web role call DotNetOpenAuth's OpenIdRelyingParty.CreateRequest method, not doing anything with its result, just to 'prime the pump'?

Going Live - Any best practice check list and how to increase security on an MVC Site?

I have been building quite a few MVC based websites locally and am finally ready to deploy the first, but, I am getting rather nervous.
During testing, I noticed several things that worried me - I am using the default forms authentication with a few tweaks (although nothing to the underlining security).
I noticed that if I created a user in one application and logged in, then launched another application... it would keep me logged in* as the user from the previous application. The user doesn't even exist in the new application!
* - I used [Authorize] on controllers, and was surprised I could just get straight in without any sort of authentication
I assume it is because the cookie is being set for localhost instead of the application/port (although, not too much I can do about this in development).
Based on this, how secure is the default authentication?
1. Is there anyway to check from the code that the user doesn't have a "faked" cookie? / Check the user has logged in from my application?
2. I was just wondering if there are any sort of check lists or anything I can go through before deploying?
Sort of - 3.As of writing this, For question 1. I am guessing I could add a column with a random number that is saved to the cookie, and then that number is checked every time any authentication is done... however, I did not want to start mucking around with the membership provider... but I think this could work. Is this a good idea?
Try using IIS on your machine instead of VS Dev Server. Solves your problem 1.
Other than that I don't think you will need any extra effort to make default membership mechanisms of asp.net to make more secure if of course you don't need a real custom things to do in your projects. These things are around for a while now and I think they have been well tested in terms of security.
You just need to remember to put [Authorize] attribute to right places. If not on your controllers put them to right methods.
Basic Web Authentication shouldn't be trusted for applications which contain truly sensitive information. That being said it's sufficient for most applications. Be sure to check your application as often as possible before and after release for XSS vulnerabilities.
Here is Microsoft's recommended "Secure yourself" list. http://msdn.microsoft.com/en-us/library/ff649310.aspx
No matter how strong your authentication is, one small XSS mistake and a malicious user can do as they wish to your site, and your users data!
I recently read a good book: Worx Professional ASP.NET, it talks about these steps in more detail on securing yourself as well as exposing examples of problems. After reading this I was able to "deface and steal" my own sites information with relative ease, was a good eye opener on the importance of securing for XSS.

How should I implement session management/authentication on Tomcat with future OAuth implementation in mind?

I'm working on a web site and I plan to use strictly OAuth in for user authentication. I've never implemented session management/user authentication before; and so - naturally - I'm reading up on a lot of how tos to get this done.
The problem I'm running into is that a lot of examples out there for doing things like setting up your realm, authenticator, etc etc seem to rely on the user/password paradigm for authentication. The whole point of going for OAuth is to avoid this in the first place!
That being said; I'm actually not looking for examples of full OAuth implementations right now. I understand that I need to understand that for myself. BUT with a future OAuth implementation in mind; how should I structure my user authentication/session management FOR THE TIME BEING in a way that will allow me to move forward on developing the functionality on my site that I really care about? I suppose I could throw some stuff together for that; but I'm just afraid that down the road I will be shoe horning an OAuth implementation as opposed to do something now which allows me to lay down the basic framework for it and then move on to other things.
So; does anyone know of a good example of laying the groundwork for OAuth on Tomcat 7? For example, which authentication mechanism (Basic, digest, etc) I should use or how I should represent user credentials in my database?
I know that this is kind of a vague question; so I'm not expecting someone to come out and tell me all of the answers I need to know. I'm just looking to get pointed in the right direction here.
Perhaps Spring Security would be useful? Your webapp could leverage Spring Security and use whatever login mechanism you need (i.e., you could do the default form-based authentication or Basic Auth for now, and replace the login/auth piece with an OAuth implementation when you're ready), but still have Spring Security manage authorization to particular resources in your webapp.
Someone has also built OAuth for Spring Security, so it may be a useful addition to your web app all around.

What would it take to make OpenID mainstream? [closed]

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed last year.
Improve this question
OpenID is a great idea in principle, but the UI and the explanation as to why it is good are currently not tailored for general use -- what do you think it would take to make OpenID work for the general public? Can this be solved with technology, or is the problem so intrinsically hard that we are stuck with difficult explanations/multi-step registration procedures, numerous accounts, or poor security?
It needs to be much simpler: involve less knowledge of the concepts, and require fewer steps - preferably zero. When the technology works with little or no assistance, it'll take off.
The mechanics of OpenID credentials, providers and suppliers shouldn't need to be exposed to the user. People talk about educating the masses of internet users, but that's never going to happen - the masses never stop being stupid. If you want to appeal to the masses, you need to bring the technology down to meet their level instead. When a Google-affiliated site picks up that you're logged into Google and silently uses that account, it works without you ever having to tell it who you are. The fact that OpenID is so clumsy in comparison is why the big providers like Google are still avoiding it, and why the general public won't adopt it.
I think the developers of OpenID messed up when they used a URL rather than an email address for the IDs. People know what email addresses are, they already have one that's associated with them (or can get one easily), and email providers like Google and Microsoft are happy to adopt a role as portals. In fact, an automatic translation from email address to URL is all it would take:
myname#example.com -> http://www.example.com/openid/myname
I think it'll take a huge buy-in from a site that millions of people use; for example, MySpace is soon supporting OpenID, so now the number of users that OpenID supports has just jumped by a huge amount. If more of the high activity sites on the net follow this lead, there you go!
ISPs should provide openIds to all their customers that mimic their e-mail addresses. Perhaps openID needs to support automatic translation of foo#example.com into http://openid.example.com/foo so that ISPs can easily set this up on a separate server.
It will take all the popular sites supporting it and making it transparent to the user.
"You can make a useraccount here, or if you use MySpace, Google Mail, Hotmail, etc then you can sign in using OpenID."
Don't sell it as a new service, sell it as being able to sign in using a different ID from another site.
The issue, however, is that with everyone supporting it each user will now have a myspace id, google id, etc. Now if they sign onto stackoverflow with their myspace id then later with google they may be perplexed that stackoverflow doesn't recognize them.
I wonder if openid has a solution for linking openid accounts so they are one and the same - I doubt the technology allows for it, since they are essentially independant signing authorities. Google would have to share data with Myspace and vice versa to enable that...
I don't think it will become mainstream. I think Ted Dziuba gets it right when he says it solves a "problem" that most people don't consider to be worth solving.
http://teddziuba.com/2008/09/openid-is-why-i-hate-the-inter.html
It will have to get a hell of a lot simpler, with easier-to-remember IDs.
You mean it isn't already? ;)
Obviously a lot of currently-popular applications would need to offer it and make it obvious that it was a good alternative.
If Google and Facebook made it an obvious option, that would help.
Ultimately, user education will really be the thing that does it. I doubt most people would care though...dumb sheeple.
Many of the responses so far seem to boil down to two options:
user education, and
forcing adoption (lots of sites changing to openid from in-house auth.)
Is that all we can do? What about distributed tools to make it easy for casual users to do openid delegation? (Say, something integrated with OS X / Windows / Ubuntu) Are there technological barriers that make this infeasible?
If client-side (and vendor-issued) applications could let you manage your on-line security preference, then we'd possibly be able to combat some of the risks associated with giving random sites your passwords -- since the "login area" would be some local program sitting in your systray, or what not. Of course, the integration of web apps with the desktop (such as that provided by Chrome) may make such a distinction impossible in practice, so it may be a moot point.
In any case, it seems like there should be something we could do now to make openid more palatable to the general public, and speed adoption in addition to making the system more user friendly.
As someone who primarily programs web apps in Java, I can't/won't use OpenID because the library support isn't there. JOID and openid4java are the only two that I know of. JOID is apparently not actively maintained, not including really important patches that have been on the mailing list for months; and openid4java requires >40 megabytes of external dependencies, including some that need to go into the endorsed classpath, which is, as one user commented, ridiculous:
Comment by witichis, Apr 28, 2008
46MB download for a simple redirect and de/encryp - are you f****n' drunk?
In my opinion, OpenID is not bad. It consolidates login credentials. It does solve a real problem, while it may not be the optimal solution The only two problems I can see are that you must trust the identity provider not to allow someone else to claim to be you, and that relying parties (web sites you log in to) can collude to link your identity on multiple sites together.
I think we need to see OpenID offered as a login method more consumer oriented websites. There are a lot of big consumer sites that can be used as OpenID providers, but the only place I recall seeing OpenID available as a login before Stackoverflow is to comment on Blogger. Being a provider is great and all, but it's pretty much invisible to consumers. Seeing an actual place to use OpenID, on the other hand, will probably garner somewhat more interest.
It would certainly help if more OpenID consumers were also OpenID providers. As a developer, I'm comfortable going through a few contortions to figure out that I can create a new ID on openid.org, but the more mainstream consumer could easily be put off by the process.
The fact that big sites will accept OpenID isn't, on it's own, enough to make it mainstream. The closest I've seen so far was having LiveJournal both accept and provide OpenID authentication (which I believe it has been doing for quite some time).
But I think that just accepting OpenID isn't enough. What we really need is more sites like this one that refuse to make their own authentication system, and require OpenID authentication. If the "next big thing" said you have to use your OpenID to log in (with a really simple wizard to set up a new ID with someone else), I believe that it will start the ball properly rolling.
Browsers should auto-fill OpenID login boxes so that you don't have to remember your ID.
Web frameworks should come with it as the default, unless you take lots of extra time to configure a simple username/password combination.
Sites that use OpenID need to put it front and center on the login page. I have seen many sites hide it behind a link under the standard login/registration page like this:
Username:
Password:
or use your OpenID
Choosing a provider needs to be much simpler.
At present there's no way to know how reliable, trustworthy or secure any of them are, or which will still be around in 6 months time.
It won't be mainstream, as it's too much effort and is too confusing for those used to email address and password.
For example:
To login to stackoverflow with Opera I have to click login, select myOpenID from the list, type my username, hit enter, press Ctrl+Enter to autofill the password on the myOpenID site, then press the continue button.
To login into any normal site with Opera I just press Ctrl+Enter to autofill the saved user/pass combo.
Im looking into OpenId right now to integrate into a start up site so it can manage the login process for my site.
I think to make this main stream they need to make this super simple. Copy, paste code into your site and it loads the login form that gives you pretty much what Stackoverflow.com does.
I think you can style up the layout of the form to be more recognizable as well.
Personally I don't think it needs to be mainstream at all, it was an interesting idea, but it is no longer relevant.
When I create a normal login, I type in my username, master password and click on the SuperGenPass bookmarklet. That is it, when I had to sign up to stackoverflow I had to find an openId provider, sign up there (which took forever) login to my website and setup delegation, then add stackoverflow to my list of sites.
And yesterday I couldn't login because I had removed the file from my webhost and they had some security issue.
Conclusion: Don't use openid.
I'd use it if I could do it per-site and aggregate the identity later on my own time and terms. As it is, it's a giant pain in the ass to even find a decent OpenID provider; by decent I mean stackoverflow.com isn't one so I'm not going to bother.
Make it less open.
i do not want the same identity on multiple sites.
i do not want to have to create a flickr account before StackOverflow will let me post.
i do not have to have to create a new flickr account for each website that i want to register with.

Resources