Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Calling [Auto Api] , response status code 302 , why not 401 ? #5235

Closed
yincen opened this issue Aug 31, 2020 · 12 comments
Closed

Calling [Auto Api] , response status code 302 , why not 401 ? #5235

yincen opened this issue Aug 31, 2020 · 12 comments

Comments

@yincen
Copy link

yincen commented Aug 31, 2020

hi,
when i calling the [AUTO API] without login, why is the response status code 302 instead of 401.
version : 3.0.5
ui : MVC
In this case, I want the response to be 401.
how can i do ?
thank you !

@hikalkan
Copy link
Member

hikalkan commented Sep 24, 2020

Hi,

Can you write your method here? For example, I am getting 401 when I try this:

image

Also, how you are calling it? Using an external tool? Please write the steps to re-produce it.

@yincen
Copy link
Author

yincen commented Oct 22, 2020

Sorry, I just saw the message now.
I don't create controller, Just create a application service
You can re-produce it by following the steps below:

  1. Create file "TestAppService" in application layer, Code:
namespace Acme.BookStore
{
    [Authorize]
    public class TestAppService : BookStoreAppService
    {
        public string GetName()
        {
            return "hihihi";
        }
    }
}
  1. Calling the API by Swagger UI
    It redirected to the login page.
    图片

@maliming
Copy link
Member

@yincen See #2643 (comment)

@hikalkan hikalkan self-assigned this Nov 2, 2020
@hikalkan
Copy link
Member

hikalkan commented Nov 2, 2020

I am reponing this since I've got a similar comment: "If you hit an API endpoint that has an [Authorize] header as an anonymous user it responds with a 200 response and an html login page instead of a 401"

@mtozlu
Copy link
Contributor

mtozlu commented Nov 16, 2020

If your api call has X-Requested-With: XMLHttpRequest header, the api will return a 401 instead of redirecting to login page.
maliming's comment above has the explanation as to why this happens.
Nevertheless, if you are not able to add the header, here is a workaround you can use for now;

private void ConfigureRedirectStrategy(ServiceConfigurationContext context)
{
	// Without this, api calls without "X-Requested-With: XMLHttpRequest" 
	// are redirected to identity server login page.
	// We want to return 401:Unauthorized instead of redirecting
	context.Services.ConfigureApplicationCookie(options =>
		options.Events.OnRedirectToLogin = context =>
		{
			context.Response.Headers["Location"] = context.RedirectUri;
			context.Response.StatusCode = 401;
			return System.Threading.Tasks.Task.CompletedTask;
		});
}

Call it in your module's (I use it in HttpApiHostModule) ConfigureServices method.

@yincen
Copy link
Author

yincen commented Nov 16, 2020

If your api call has X-Requested-With: XMLHttpRequest header, the api will return a 401 instead of redirecting to login page.
maliming's comment above has the explanation as to why this happens.
Nevertheless, if you are not able to add the header, here is a workaround you can use for now;

private void ConfigureRedirectStrategy(ServiceConfigurationContext context)
{
	// Without this, api calls without "X-Requested-With: XMLHttpRequest" 
	// are redirected to identity server login page.
	// We want to return 401:Unauthorized instead of redirecting
	context.Services.ConfigureApplicationCookie(options =>
		options.Events.OnRedirectToLogin = context =>
		{
			context.Response.Headers["Location"] = context.RedirectUri;
			context.Response.StatusCode = 401;
			return System.Threading.Tasks.Task.CompletedTask;
		});
}

Call it in your module's (I use it in HttpApiHostModule) ConfigureServices method.

Thank you. This is what I want.

@maliming
Copy link
Member

hi @mtozlu

For Angular you can try to configure the DefaultAuthenticateScheme and DefaultChallengeScheme .

services.AddAuthentication(options =>
{
      options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
      options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
})
.AddJwtBearer(options => //......

@sebitsi
Copy link

sebitsi commented Jan 20, 2021

Hi @hikalkan @maliming
What is status of this issue ?

@mtozlu post workaround. But this is only workaround.
And response body is still different than in native controller response.

Are you preparing some update to achieve same behavior when calling controller vs. dynamicaly created from appservice ?
When calling ABP API from outside world there shoudn't be difference if i made constroller or it has been created dynamicaly from appservice.

@maliming
Copy link
Member

This is follows the AspNet Core design.

#2643 (comment)

@sebitsi
Copy link

sebitsi commented Jan 21, 2021

@maliming Thanks for your answere.
I understand your comment.

But calling native controller or dynamicaly created should return same response. Right ?

{
  "error": {
    "code": "Volo.Authorization:010001",
    "message": "Authorization failed! Given policy has not granted.",
    "details": null,
    "data": {},
    "validationErrors": null
  }
}

Why you decided to return login page (redirection) ? What's the case ?

How i can extend workaround that return same response that native controller (error json) ?

@maliming
Copy link
Member

#9940

@laosandegudai
Copy link

hi @mtozlu

For Angular you can try to configure the DefaultAuthenticateScheme and DefaultChallengeScheme .

services.AddAuthentication(options =>
{
      options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
      options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
})
.AddJwtBearer(options => //......

This is very useful and I use it for CRUD App Service

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

No branches or pull requests

6 participants