SPA calling a WebAPI calling a WebAPI - oauth-2.0

I am building a SPA (javascript) which will call WebAPI A (.net MVC API) and which in turn will call (server side) WebAPI B (.net MVC API).
All three entities are protected by ADFS4 (OAuth2). In my workflow I want WebAPI A to call WebAPI B on behalf of the user who has logged into the SPA.
In reading the various documentation by Microsoft I found that the scenario described in the following article applies best to my case:
https://learn.microsoft.com/en-us/windows-server/identity/ad-fs/development/ad-fs-on-behalf-of-authentication-in-windows-server
The article assumes that the client application can perform the authorization grand flow. Nevertheless in my case I am dealing with a SPA which should be using the implicit flow of OAuth2. In addition even if I wanted to use the authorization grand flow I would still need to do a POST on the token endpoint of ADFS from the SPA which is not possible as ADFS4 does not offer a way to add CORS headers. I could of course deploy a proxy in front of it and add the headers... I have not explored this option yet.
I found a solution to make this work but it seems more like a hack to me; The SPA during login requests two tokens (1 for WebAPI A and 1 for WebAPI B) from ADFS4. It passes both tokens to the WebAPI A which knows that the 2nd token is for accessing WebAPI B.
Does this solution seem correct? Should I be doing something differently?
Thank you!
PS:
1) SPA cannot accesss directly WebAPI B as it is accessible only internally.
2) Assume I have total control over development on all three entities.

it's not a good idea to use the authorization code flow for SPA application, because you have to really keep the secret key that can generate access_token, which is not secure in that case.
i suggest that you use the implicit flow for you spa application and between your servers use the authorization code flow, this way you are sure about security

Related

Can I use OIDC Hybrid Flow While Serving Angular SPA from ASP.NET Core MVC Project?

I've got 2 different .NET Core 2.2 MVC projects. I'm using IdentityServer4 for the token server, Azure B2C for the identity store.
The 1st MVC app is a normal MVC application, and I've got it working perfectly with the OIDC Hybrid flow.
The 2nd MVC app is an Angular 7 cli app, which serves up the index.html and houses the API that the app will be calling. The angular app will not call any other APIs directly (gateway pattern).
My questions are about the 2nd app - I'm trying to figure out the best way to set up the Angular app for security.
My understanding is: OIDC Implicit flow exposes exposes the access token on the browser. OIDC Hybrid flow does not expose the access token (at least when hitting the same web server - no CORS), because the web server (client) uses the back channel to obtain the access token, via the authorization code, and its never exposed to the browser.
QUESTION #1: Is my understanding of Implicit vs. Hybrid correct?
If my understanding is correct, I'd think the best way to go would be Hybrid flow even for the Angular app, but most samples I've seen for using OIDC with Angular involve the Implicit flow, and don't take advantage of the authorization code / backchannel. Avoiding having an access token on the browser seems like a big deal, like a worthy goal, but wondering why it doesn't seem to be done?
QUESTION #2: I'm serving up my Angular index.html from my MVC server - why can't I just use Hybrid flow to protect the index.html page, and keep the token on the backchannel?
Something tells me my understanding of all this isn't quite complete...
Your understanding is correct. You can protect your index.html. The only problem you will face that way is that it's not the default configuration for today. With your requirements, most likely you don't need any of oidc client libs at all, you can protect your (only) API with a (same-site, http-only) cookie (not a bearer token) and in your Angular guards just ensure that you are still logged in to your back (if not, redirect through a local MVC resource to involve server-side code into login procedure).
See this question, especially the comments and link below for further reference.

Is it ok to forward a JWT between two custom services?

I'm using Azure AD Implicit Flow for authentication between a SPA and a WebApi.
I want to know if it would be ok/save to redirect from the SPA to a intermediary service of my own as well with the BearerToken, and forward once more, from there, the Bearer token to the WebApi.
If they belong to the same security domain (i.e. under control by the same entity) in principle that is not a problem. You should take precautions against token leakage/exposure, as always.

web api authentication in MVC application?

I'm confused on how the Web API implements the authentication?
I have gone through the links 1.
Link1
Link2
and need to summarize what I understood.
Owin katana is a mechanism that can be implemented for authorization.
There will be Iprincipal which can be created either in the host or
in the httpmodule which will be attached to the currentthread to
validate.
Token based authentication implements owin.
I have very little idea about the authentication mechanism in web api. If someone can help me to understand this, It would be great.
I have the following doubts.
Owin is a new way of authentication in MVC? or its already exists as
a part of windows and form based authentication?
If I wrote a module to authenticate what are the different ways I can use to authenticate an api method/controller?
The answer to your question could be quite big, I will try to give you some guidelines:
Katana is Microsoft's implementation of the OWIN standard
https://learn.microsoft.com/en-us/aspnet/aspnet/overview/owin-and-katana/getting-started-with-owin-and-katana
Token based authorization is supported by OWIN and , therefore, by Katana.
There are two very usual ways to implement this token authorization, you can use Windows Authorization
https://learn.microsoft.com/en-us/aspnet/aspnet/overview/owin-and-katana/enabling-windows-authentication-in-katana
or you can use a more standard and recommendable way using OAuth:
https://learn.microsoft.com/en-us/aspnet/aspnet/overview/owin-and-katana/owin-oauth-20-authorization-server
With ASP.net (netfx, not core), you use attributes on controller level to provide the metadata necessary to implement the authorization and authentication.

Authentication-Authorization issue when dealing with WebAPI

I'm re-developing an app as a web app (the "previous" iteration was in VB6) to run on azure. One requirement is that we only use facebook/google authentication (OAuth 2.0). Another business requirement lead me to break my project into the following schema:
1 Project for the WebAPI 2.0
1 Project for Controllers
1 for Data Access (typical layer pattern)
N Projects for MVC 5 front-end
The idea is that the MVC projects will only consume the WebAPI via javascript/json! The N MVC projects will contain just the GET implementation for the pages. No models or others actions (post for example). In other words the MVC projects are completally disconnectd from the other projects and should have no intelligence what-so-ever!
This is the selected way because of (bitchy clients and) limited time constraints.
Anyway, as you can notice the "core" (WebAPI + controllers + DA) is shared. The core is in fact a multi-tenant service. (but remember the disconnected facet!)
My problem here is: How do I handle Authorization? What/how should treat the passing of the claims between the MVC projects and the WebAPI? Im lost here. After some thought, I came to the conclusion that I need to make the WebAPI project act as a proxy here, something like:
Random users lands on www.myClientWebsite.com/Register
Chooses a login provider
The MVC project redirects the user signaling facebook to return to www.myWebAPI.com/Register
I intercept the claim and redirect the user to the original www.myClientWebsite.com/LoginComplete or something...
Am I getting it wrong?
You have to use OAuth 2 for authentication and authorization purpose in this scenario. Yes, you should be making the authentication at the MVC level and then use tokens to keep the security intact for rest calls.
Here your MVC application should get a Bearer token from the identity provider like google and then hide it some where on the form. Then for every jquery request you make to web api, you have to send this bearer token in the request.
[Update]
This is considered kind of hack and I do not encourage it. And this works only if both the systems are in same domain.
[\Update]
If both MVC and Web API are on different domains, then you can think of using Azure ACS Service Identity to build the trust between domains. Then pass the bearer token of User claims in the payload of the request.
[Update]
This is much more better way to handle this but must be accompanied with proper token revocation and https security.
[\Update]

How to secure WebAPI inside MVC 4 .NET SPA template with token-based HTTP basic authentication?

I've been reading different articles on the subject of securing WebAPI, including:
leastprivilege article
kevin junghans article
piotr walat's article
and many others.
I would like to use the MVC 4.NET SPA template (with either Backbone.js or another JS lib) and I'd like to secure WebAPI used by SPA with basic http authentication, using tokens in the headers because some of the WebAPI clients will not support cookies required by forms authentication.
The SPA template uses SimpleMembership and oauth, which I would like to use and combine with basic http authentication.
What's unclear to me is whether the SPA template out-of-the-box authenticate and authorize WebAPI with basic HTTP authentication and tokens, or do I have to follow and piece this together from the links above?
This is quite a large topic and its best to completely understand it before simply plugging in templates.
Here is a great video to help put everything in place: https://vimeo.com/43603474
You must be using SSL for any token based authentication (like oAuth)
Once the user is authenticated - via oAuth or your own membership provider, you can simply attribute any Web Api methods with [Authorize] to ensure that a non-authenticated user can't call those methods (will return a 401 - not authorized if not authenticated)

Resources