I have an older webapp that has implict flow I need to continue to support. I tried to use Microsoft.Identity.Web 1.9.0.0 but it does not allow me to use id_token it requires only access token in the authorization header I get the error message below :
[10:09:31.861 -04:00] [ERR] [] [] An unhandled exception has occurred
while executing the request. System.UnauthorizedAccessException:
IDW10201: Neither scope or roles claim was found in the bearer token.
at
Microsoft.Identity.Web.MicrosoftIdentityWebApiAuthenticationBuilderExtensions.<>c__DisplayClass3_1.<b__1>d.MoveNext()
Is there a setting to allow it? I couldn't see one in JwtBearerOptions or MicrosoftIdentityOptions.
It does work when I use Microsoft.AspNetCore.Authentication 3.1.0.0 library, but I wanted to have newest library possible. Any recommendations would be great.
Edit: More details
Our company is under major tech shift. he have built alot of stuff in .net core and web components (Polymer) for front end but . We decided to switch to Azure AD B2C. We have no problems switching our .net core and existing polyymer UI's to authorization code flow.
We have alot of assets in .net web forms. Those Web Forms are large projects that are using forms Authentication membership. We don't have the resources to switch all the UI's to Web Components and .net core at one shot. The plan is switch the identity to Azure AD B2C and release it to production. When there is a change request or new feature request we would build the new pages only in HTML and Web Components (Polymer) and have a .net core api to handle those api requests. The problem is that the Web Coponents doesn't have access to the access token.
The solution I found was when the Web Forms gets a responds from B2C I conect OpenIdConnectAuthenticationNotifications to SecurityTokenReceived which reads the IdToken and I put it in a cookie with an expiry in (30 seconds) and return it to the browser. I have javascript code that reads to see if the cookie exists and takes it and stores it in the Session Storage and deletes the cookie. Also on load the browser checks if the user is signed in if not it deletes the Session Stored id_token.
This works as expected, but the problem is it is using the id_token and not using the authorization code flow. So When accessing any other api I can't request a token from B2C for the other API. Also I can't get a refresh token (plan is to set it to 8hrs to expire which is good enough). I have looked at if it's possible to make it work with code flow. i have looked at how it works in MVC but it I haven't made it work,
This is the project I used to switch to B2C https://github.com/AzureADQuickStarts/B2C-WebApp-OpenIdConnect-DotNet
After deciding to give up on this. Working on a different project I had to run a cross this issue. Decided to do another search and found this post
https://github.com/AzureAD/microsoft-identity-web/wiki/web-apis#to-support-acl-based-authorization
through this Stack overflow Q/A
IDW10201: Neither scope or roles claim was found in the bearer token
this is what is needed to use the latest Microsoft.Identity.Web Package. To sum it up in the you need to set the Azure options variable AllowWebApiToBeAuthorizedByACL = true
The error message expects scope or roles in the bearer token. Please follow this document for implicit flow versus authorization code flow concept.
https://learn.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-implicit-grant-flow
Related
I have a Cognito user pool, an app set up and a resource server set up. We do not want to use the hosted UI to log in and I am trying from the back end to authorize with Oauth 2.0 with a user name and password and send the token back to the front end to use with api gateway calls. I am using c# and the provided SDK does not allow for the right scope, so I am trying the manual oauth2 method of logging in, but nothing I have tried is working.
Edit:
I have gotten a bit further today trying to use postman, however, I am getting the error: unsupported_grant_type with the following setup:
As of now, this is not supported without hosted UI. Basically, you can not expect AdminInitiateAuth to include custom scopes in the access_token.
This is not a limitation in .NET SDK. This is a limitation in Cognito itself.
As per this answer, someone can argue that this the intended behaviour.
Signing in via initiate Auth or admin initiate Auth is not via the Oauth endpoints so the Oauth custom scopes will not be included in the token.
Also this issue has been mentioned in different other SDKs/Libs like: android sdk, Amplify JS as well. Several issues are mentioned in this comment.
Maybe you could try to use id_token along with Lambda Authorizers as a workaround.
I am trying to create a full stack app (with React.js on frontend and ASP .NET Core Web API on the backend). The login process needs to be done using Active directory, as users are employees within a single organization. Frontend must get a token (using a MSAL library) and then send it to backend, where it has to decode it and, basing on it recognize user and register every session in the database, and let users perform actions set with their roles. Those roles, need to be assigned in database.
Does anyone know how to do that? Even an example project like that would help me immensely, because everything I have found so far is very basic.
For implementing the authentication in Asp.net core follow this doc here.
Authorization in Azure AD can also be done with Application Roles. Application Roles in Azure AD are by no means mutually exclusive. They can be used in tandem to provide even finer grained access control.
In your react-app (client) you can get the token, then access webAPI with the token. You can then take a look to this source code.The only different will be that you will call your own webAPI instead of Microsoft graph.
For controlling the authentication session read more here link.
I am new to .NET core and while I have .NET experience, I have never built authentication, in the past I've always worked on project not started by me. I am just trying to learn and find good resources and I would greatly appreciate if anyone knows tutorial or if it can explain how to solve this.
When using external logins, I followed those instructions here. This all works well if I create simple web api project and run, I get a web page where I can login, authenticate, works perfect. But this is not my end goal, I am building Web APIs not a Web Application. In my case let's say I have iOS and Android apps and my external login is done on the app itself, how would I pass token to Web APIs? I want to use [Authorize] method in Web APIs to make sure that no un-authorized access is made agains APIs and in addition to that I would like to use roles.
I am assuming token information is passed in header. But what is the header name for token? Can external authentication be used with roles or that is only possible if I store username/password? Can you point me to some good tutorial or anywhere I can learn more because all google search returns back to same like I have mentioned above and it is not very descriptive.
In general , your web api will work like a identity provider , it will issue and validate the JWT tokens :
http://bitoftech.net/2014/06/01/token-based-authentication-asp-net-web-api-2-owin-asp-net-identity/
You can also implement authorization with the help of your external login provider .If you have SDK or own code in your client app to help do authentication , for authorization part , you can also register your web api in the same identity provider . For example , you are using the google authentication external login in your client app , you will should register your client app and web api on google's application registration page , then you could use OpenID Connect hybrid Flow to authentication user and get access token for accessing web api . Each identity provider provides how to implement authentication/authorization with lots of documents.
You can have an endpoint that allows anonymous access and takes the token and verifies it. Then it can send back a JWT that contains claims/roles that you want to enforce on the specific user. Every time the client accesses a secure endpoint, it can send your JWT in the header which gets verified before the specific method in your API controller is called. You can look into OAuth flows if you want to integrate social logins.
For example, Google has this documentation for OAuth-
https://developers.google.com/identity/sign-in/web/backend-auth
We have an application built on a static front-end and an API hosted under a separate subdomain (e.g. web.theapp.com vs api.theapp.com). We've recently implemented a document management component built on top of Azure Blob Storage, with custom metadata in the API. When downloading a file, we want the user to get to the API (for authorization checks etc) but then be given/redirected to a blob storage URL with a short-lived SAS token. We have the API part "done" insofar as we can accept a request, do all the required access checks, create a SAS and generate an URL to the file, and redirect there.
HOWEVER: For authentication in the API currently uses Bearer tokens, which obviously won't work on GET requests that result from clicking on links.
Is there a good "goto" solution for this type of problem?
We've been thinking about creating a page saying "Your file downloads in 3... 2... 1..." like the old-school hosting services, but that feels a little tacky. We've also considered adding some sort of cookie scheme, so the API can accept authentication either with bearer tokens or with cookies, but we've failed to find info on how to configure cookie authentication (relevant tech stack: Azure AD OAuth2 and ASP.NET Web API 2).
Is there a good pattern for this type of problem?
I'm writing a tutorial of using IMAP XOAUTH2 authentication in .NET (the standard MVC5 web app which is created by the MVC5 wizard).
I now have all parts except access_token from which I'll create XOAUTH2 IMAP key (the app authenticates, token seems to get refreshed if required, and I know how to build XOAUTH2 IMAP key and do IMAP login when access_token is available). I just need that token.
Although I have some ideas how this can be done I need to make sure I'm not doing anything stupid. For instance, I think I can use something like context.Identity.AddClaim in ConfigureAuth to put the access_token to our identity and then get it from there when doing IMAP login (on another page) but not sure if this info isn't already available.
Maybe, I can have access to that access_token in any place in the code without the need to manually put it in some object (which would be redundant and look silly for a reader experienced in OWIN and MVC5)? I develop .net components for SMTP/IMAP, I'm not a MVC5 expert, just need to write a simple example for using my IMAP lib with it.
Well, looks like saving access/refresh token details in ASP.NET Identity database makes sense anyway (despite the fact is's stored in encrypted cookies). This lets the access token data be accessible even when the browser is not available. For instance, if someone registers in a web app with their Google and Microsoft account and then another app (e.g. Windows service) consumes the access token initially retrieved by the web app to access the user's account (to check for new e-mails or whatever).
Also, it's possible to make sure both versions of access token details (in ASP.NET Identity database and cookies) stay in sync. This is useful if the access token gets updated with a refresh token (as access tokens need to be updated every hour). The standard ASP.NET MVC5 app cannot refresh access access tokens so you need to refresh them by your own code. I extended ASP.NET MVC5 template with refresh tokens, saving access/refresh tokens in ASP.NET Identity database and updating access tokens in cookies to make sure that access tokens in both locations match.
If anyone interested, you can grab some code and explanations at:
http://www.afterlogic.com/mailbee-net/docs/OAuth2RegularAccountsWebApps.html#SyncingTokens