Identityserver4 Access levels Practices - asp.net

We're looking for 3 types of different access levels but don't know how to implement them using current identityserver4 features.
Have these scenarios:
We have an upper management system which some clients have access to specific pages or not, like admin or client(seems like Roles)
We have column type access level, for example, some users in the manager role can see a specific column/field or not, or in same roles shouldn't see some column/row data in reports.
We have a record level, access level, for example, some manager shouldn't see other branch client list. (like policies)
The whole process should be dynamic without any hardcode. and for doing these structures we should do some code on the back-end(middleware, etc) and some on frontend side(with a razor or etc).
any Idea how to implement these using identityserver4 authorization types?

The main feature of IdentityServer is to handle the authentication of the user and global authorization: which client has access to what resource.
Everything else could be considered out-of-scope of IdentityServer. Please read this article for some background information.
As an answer they've created the PolicyServer.
In the OSS version authorization has become a seperate (local) mechanism, while the paid version outsources authorization to a seperate server.
Extended with resource-based authorization you can implement authorization that covers all access levels.

Related

OAuth To .Net Core Api User Mapping

I work for a company that supports many applications, but for ease for users has an OAuth OIDC Single-Sign-On (IdentityServer4) so they can log in once and access many applications of ours. I have no problem configuring authorization to this OAuth with the returned JWT/Access Token.
But because our support footprint is so large, we have been told to handle roles, and user permissions at the application level. Here is where I am asking for feedback. I am currently developing a new API in .Net Core 6 (newbie to building APIs), and am wondering best practice for connecting a essentially third party OAuth, but also utilizing roles and permissions specific to the application.
The Identity Server returns a JWT/Access Token that is passed to API in form of bearer, but I need a mapping on the .net core backend to map the User contained in the JWT with a user within the application. Then the application can have separate mappings for roles/permissions, and utilize those roles as restrictions within the API, but I am not sure what best practice would be for this that also maintains the best security, while also achieving best performance. My thought was creating a middleware that creates and overrides userIdentity, but with that happening each call seems like unnecessary overhead. The other option is dual auth with cookie based auth that is set once, but am just unsure of best way, or what others have had success with. I know this must be a common flow that I am overthinking. Any insight is greatly appreciated.
It is common in many mature business systems to integrate identity and business data as you describe. There are two main techniques:
Identity system reaches out to business data at the time of token issuance, to get custom claims to include in access tokens. This Curity article explains the approach.
APIs look up custom claims, eg from a database, when an access token is first received, then cache custom claims for subsequent requests with the same access token. See this .NET code of mine for one way to do this.
In both cases the end result should be that the API business logic gets a useful ClaimsPrincipal that enables the correct authorization, as in this example class.
Finally, from an information disclosure viewpoint, aim to avoid returning detailed claims in JWTs to internet clients. It is common to use opaque access tokens instead, as a privacy preserving pattern.

OAuth2 protected API. How to allow customer's to SSO using its own authorization server?

I have an Angular Single Page Application (SPA) talking to my ASP.NET API.
The API is protected by my own Oauth2 server (IdentityServer4).
One of my customers (let's call him X) wants SSO: Their users on my platform would sign in on their server instead of using the login form in my app that connects to my IdentityServer.
Each customer has its own subdomain for the Angular SPA (e.g. x.myapp.com). Therefore I can easily redirect X's users to their server's authorization page to approve my API, based on the hostname.
However the API itself uses one common hostname for all customers(api.myapp.com). Customers are distinguished by the Origin header of the API call (x.myapp.com) during the login call (and a few other unprotected calls) and by the Bearer token for protected calls to the API.
How does my API introspect the Bearer access token? Who should know which server to query ?
Is it the responsibility of the API server? Or can I tell my IdentityServer about X's oauth2 server ?
X's users would also be defined on my platform since we need specific info (such as config of roles on the platform). My current setup implies specific claims (such as user id) that allow my API to know what the user can do. Obviously, X's server will not provide the same claims. How can I connect the dots ? e.g. get some standard claim from X's server (username, email, whatever) and match it to my list of users.
Note: This question is similar but the answer is not accepted and seems to imply that the provider of both identity servers is the same (not the case here).
Formatting my comments as an answer:
From reading your question it's pretty much clear to me that you could benefit from what is know as Federated identity.
As you said, one of your customer want to achieve SSO - They want users to login using their existing accounts and be able to user your systems normally.
Since you already have an IdentityServer in your domain, what you can do is delegate the login part to the customer's side (whatever they do it). This is illustrated in the Identity server documentation Federation Gateway.
Basically, the approach is that upon hitting the "login" button in your front-end, you would redirect the users to your Identity Server passing some special params (prompt and acr_values for ex) which in turn, tells identity server to redirect the user's to the external Identity provider (the customer's). After a successful login, you have a chance in Identity Server to augment the claims, maybe using something they returned or anything really. Then the process is as normal - you return a JWT Token generated by your Identity Server
The benefit of doing this is:
Your SPA/API doesn't have to change. You will still work with your own bearer tokens and can continue doing authN/AuthZ as before.
You have a chance to add claims that might indicate where this user is coming from if needed
If your customer's server changes, you don't have to worry much, apart from maybe some tweaks related to returned claims
They don't necessarily need to use OpenId/OAuth on their side for this to work
Useful things you probably will need is some params to pass during the call to the authorize endpoint in Identity Server. (acr_values and prompt).
You can also check this in the quickstarts, by looking at Sign-in with external providers (which is pretty similar to what you want)
Now to your individual points:
Your Identity Server should be the "bridge" between you and the customer's "identity provider".
Upon a login from an external provider (X), you need to somehow identify the user on your platform. You could use email or, even better, if X is already using OpenId/OAuth they might give you the sub claim which is the user id on their side. At this point you need some sort of agreement with them otherwise this might be flaky/unreliable for both sides.
In a more "advanced note" you could also add to your tokens some sort of claim that tells you who is the source provider of this user. Here the source provider would be X. This is useful because you might want, for example, configure allowed identity providers in your app, or maybe enable features only for certain providers. Like, ppl logging in with Google might only see certain parts of the app.

Securing ASP .Net Web API for usage with mobile application

I am currently using Token based authorization via OWIN to keep my APIs from being exposed to everybody.
However, there is a flaw attached to this method. Once a user gets a token, he can access any API across my website and get the response for any parameters posted; which is dangerous in my case.
Right now, I need to give API access to my mobile application but I want to strengthen the security of my APIs in such a way that the requests are filtered based on user access.
Use case:
I generate a token when the user logs in and will append it with each request to the API. It works absolutely fine but... the generated token can be used to fetch the details of any other user.
What I want to achieve:
I want to prevent the above case from happening. I want to filter the illegal requests/responses to/from API.
How do I go about it? How do mobile apps generally restrict users from accessing their API. I am very interested to know about it. Please guide me.
What you have implemented till now is only authentication part, it is not going to help you much for securing your website, to implement security in proper way you need to do proper authorization also.
For this you need to implement following things.
RBAC - Role Based Access Control in your web api actions, by this you can achieved using the default Authorize filter provided by the framework.
For example
[Authorize(Roles = "Administrator")]
public void DoSomething()
{
}
If you are using OWIN, you can set the roles in GrantResourceOwnerCredentials method like following
identity.AddClaim(new Claim(ClaimTypes.Role, "Administrator"));
Data Level Security: This is very important, as people belonging to same role can access only a set of data, to implement this type of security, the best place is your database. You can implement Row Level Security/Cell Level Security in your database, or you can restrict the access of data based on logged in user from your database directly.
Implementing Data Level Security is not straight forward as it is driven through your business requirements (Who can access what). Out of the box no framework will be able to give you complete solution, you need to implement rules by yourself only.
Apart from above two points, you can also consider looking Cross-Site Request Forgery (CSRF) and Data integrity between server and client.

Should I use claims to reflect an authorized user with no special roles, and if so, how?

I'm currently using ADFS and claims-based identity in ASP.NET web applications to convey informations such as a user's name or identifier.
In addition, inside applications a ClaimsTransformer adds a couple more claims that are relevant to that app. Such claims include applicative roles (Admin, Validator, etc.), whereby the user can't see some pages unless they have the right role.
However, just because you have no role doesn't mean you can't access the application at all. Vanilla users that aren't part of a specific group are sometimes also able to see some pages. Besides, we have a few web applications where roles aren't used -- it's just a matter of whether you can get in or not. We call this "access", which is different from "role" or "permission".
Access rights to applications are stored in a separate database. You can have access to an application if an admin manually granted it to you or if you satisfy a set of rules calculated by another system.
How would you materialize access in terms of claims? A claim type like HasAccess with a true/false value sounds weird and vague.
Is claims-based identity the right place to look at? The idea is to insert that information precisely enough in the authorization chain that every auth cookie doesn't have to carry a list of all accessible applications for the user, but early enough in the process that an accessibility check doesn't have to be done at each http request.

Authentication against multiple identity providers using WSFederationAuthenticationModule for asp.net

We have multitenant asp.net MVC web site which supports multiple partners. Currently we are using forms authentication to authenticate users. Now some of the partners have asked for single sign on support with SAML.
I did quick POC to test it against “Thinktecture” identity provider. All I did was to install “Identity and access” extension for VS 2012 and configure the identity provider. I noticed that the extension added configuration settings like URL of the IP and realm in the web.config file. It also added “WSFederationAuthenticationModule” module to handle the authentication. This module was handling all the redirects and the validation of response behind the scene.
In my case since we will have multiple identity providers, depending upon the partner, I will be choosing the Identity provider. The URLs of the different IPs will be stored in the database. I cannot list all the IPs in web.config. Hence I need mechanism in which I can redirect user to appropriate IP URL and once the IP posts back the result, verify the result and retrieve user information through claims. I don’t want to do the XML parsing of the result and validate the response, but just want to call methods in “WSFederationAuthenticationModule” to do the heavy duty work. But I am not sure which methods will be useful for me. Can somebody help me out or list of the sequence of methods I need to execute to achieve this?
Take a look at my simple example
http://www.wiktorzychla.com/2014/11/simplest-saml11-federated-authentication.html
The trick is not to have the WSFam module in the pipleline but rather use its api to trigger redirects and consume responses. If you follow my code, you'll see there are two clauses
// wsfed response or not
if ( !fam.IsSignInResponse(...) )
// redirect to provider
else
// create local config and validate the incoming token
This simple example is perfectly suitable for multitenant scenario, in fact we use ws-fed daily in multitenant environment and most clients are based on this core approach.
Namely, creating the SecurityTokenHandlerConfiguration programatically in the branch that consumes the response gives you total control over how you validate tokens for different tenants.

Resources