Development Tip

405 메서드가 허용되지 않는 웹 API

yourdevel 2020. 10. 4. 13:36
반응형

405 메서드가 허용되지 않는 웹 API


이 오류는 매우 일반적이며 모든 솔루션을 시도했지만 그중 어느 것도 작동하지 않았습니다. 제어판에서 WebDAV 게시를 비활성화하고이를 내 웹 구성 파일에 추가했습니다.

  <handlers>
  <remove name="WebDAV"/>
  </handlers>
  <modules runAllManagedModulesForAllRequests="true">
  <remove name="WebDAVModule"/>
  </modules>

오류가 계속 발생합니다. 이것이 컨트롤러입니다.

   static readonly IProductRepository repository = new ProductRepository();

    public Product Put(Product p)
    {
        return repository.Add(p);
    }

방법 구현 :

 public Product Add(Product item)
    {
        if (item == null)
        {
            throw new ArgumentNullException("item");
        }
        item.Id = _nextId++;
        products.Add(item);
        return item;
    }

그리고 여기에서 예외가 발생합니다.

client.BaseAddress = new Uri("http://localhost:5106/");
client.DefaultRequestHeaders.Accept.Add(
new MediaTypeWithQualityHeaderValue("application/json"));      
var response = await client.PostAsJsonAsync("api/products", product);//405 exception

어떤 제안?


클라이언트에서 게시 중입니다.

await client.PostAsJsonAsync("api/products", product);

PUTing이 아닙니다.

웹 API 메서드는 PUT 요청 만 허용합니다.

그래서:

await client.PutAsJsonAsync("api/products", product);

나는 같은 예외가 있었다. 내 문제는 내가 사용했다는 것입니다.

using System.Web.Mvc; // Wrong namespace for HttpGet attribute !!!!!!!!!
[HttpGet]
public string Blah()
{
    return "blah";
}

해야한다

using System.Web.Http; // Correct namespace for HttpGet attribute !!!!!!!!!
[HttpGet]
public string Blah()
{
    return "blah";
}

DELETE 메서드 작업을 얻기 위해 많은 것을 시도했습니다 (웹 API를 허용하지 않는 405 메서드를 얻었습니다). 마침내 [Route ( "api / scan / {id}")] 를 제 컨트롤러에 추가했고 제대로 작동했습니다. 이 게시물이 도움이되기를 바랍니다.

     // DELETE api/Scan/5
    [Route("api/scan/{id}")]
    [ResponseType(typeof(Scan))]
    public IHttpActionResult DeleteScan(int id)
    {
        Scan scan = db.Scans.Find(id);
        if (scan == null)
        {
            return NotFound();
        }

        db.Scans.Remove(scan);
        db.SaveChanges();

        return Ok(scan);
    }

내 문제는 WebAPI의 속성 라우팅으로 밝혀졌습니다. 사용자 지정 경로를 만들었고 WebAPI가 POST라는 것을 발견하는 대신 GET처럼 처리했습니다.

    [Route("")]
    [HttpPost] //I added this attribute explicitly, and it worked
    public void Post(ProductModel data)
    {
        ...
    }

나는 그것이 어리석은 일이어야한다는 것을 알고 있었다 (하루 종일 소비)


Chrome은 종종 OPTIONS게시물을 작성하기 전에 통화를 시도합니다 . CORS 헤더가 올바른지 확인하기 위해이 작업을 수행합니다. OPTIONSAPI 컨트롤러에서 호출을 처리하지 않는 경우 문제가 될 수 있습니다 .

public void Options() { }

이 오류는 서버가 https에있는 동안 http에 연결하려고 할 때도 발생할 수 있습니다.

내 get-request가 괜찮 았기 때문에 약간 혼란 스러웠고 문제는 사후 요청에만 존재했습니다.


GET 호출에서 405를 얻었고 GET 서버 측 메서드에서 매개 변수 이름을 지정 Get(int formId)했으며 경로를 변경하거나 이름을 변경해야 한다는 문제가 나타났습니다 Get(int id).


메소드가 매개 변수를 예상하고 전달하지 않는 경우에도 405 오류가 발생할 수 있습니다.

작동하지 않습니다 (405 오류).

HTML보기 / 자바 스크립트

$.ajax({
         url: '/api/News',
         //.....

웹 API :

public HttpResponseMessage GetNews(int id)

따라서 메서드 서명이 위와 같으면 다음을 수행해야합니다.

HTML보기 / 자바 스크립트

$.ajax({
         url: '/api/News/5',
         //.....

다음과 같은 경로가있는 경우

[Route("nuclearreactors/{reactorId}")]

메소드에서 정확히 동일한 매개 변수 이름을 사용해야합니다.

public ReactorModel GetReactor(reactorId)
{
 ...
}

정확히 동일한 매개 변수를 전달하지 않으면 경로가 요청과 일치하지 않고 WebApi가 허용 된 다른 HTTP 메소드를 사용하여 다른 컨트롤러 메소드에 도달하기 때문에 "405 메소드가 허용되지 않음"오류가 표시 될 수 있습니다.


여기에 하나의 해결책이 있습니다.

<handlers accessPolicy="Read, Script"> <remove name="WebDAV" /> </handlers>

docs.microsoft.com 솔루션 문서

및 모듈에서 WebDAV 제거

<remove name="WebDAVModule" />


나는이 파티에 늦었지만 위의 어떤 것도 대부분의 경우 실행 가능하거나 작동하지 않았기 때문에 이것이 마침내 나를 위해 해결 된 방법입니다.

사이트 / 서비스가 호스팅 된 서버에서 기능이 필요했습니다! HTTP 활성화 !!!

Server Manager > Manage > Add Roles and Features > next next next till you get to Features > Under .NET (each version) tick HTTP Activation. Also note there is one hidden under >net > WCF Services.

This then worked instantly! That was melting my brain


This does not answer your specific question, but when I had the same problem I ended up here and I figured that more people might do the same.

The problem I had was that I had indeliberately declared my Get method as static. I missed this an entire forenoon, and it caused no warnings from attributes or similar.

Incorrect:

public class EchoController : ApiController
{
    public static string Get()
    {
        return string.Empty;
    }
}

Correct:

public class EchoController : ApiController
{
    public string Get()
    {
        return string.Empty;
    }
}

[HttpPost] is unnecessary!

[Route("")]
public void Post(ProductModel data)
{
    ...
}

I could NOT solve this. I had CORS enabled and working as long as the POST returned void (ASP.NET 4.0 - WEBAPI 1). When I tried to return a HttpResponseMessage, I started getting the HTTP 405 response.

Based on Llad's response above, I took a look at my own references.

I had the attribute [System.Web.Mvc.HttpPost] listed above my POST method.

I changed this to use:

[System.Web.Http.HttpPostAttribute]
[HttpOptions]
public HttpResponseMessage Post(object json)        
{
    ...
    return new HttpResponseMessage { StatusCode = HttpStatusCode.OK };
}

This fixed my woes. I hope this helps someone else.

For the sake of completeness, I had the following in my web.config:

<httpProtocol>
    <customHeaders>
        <clear />
        <add name="Access-Control-Expose-Headers " value="WWW-Authenticate"/>
        <add name="Access-Control-Allow-Origin" value="*" />
        <add name="Access-Control-Allow-Methods" value="GET, POST, OPTIONS, PUT, PATCH, DELETE" />
        <add name="Access-Control-Allow-Headers" value="accept, authorization, Content-Type" />
        <remove name="X-Powered-By" />
    </customHeaders>
</httpProtocol>

We had a similar issue. We were trying to GET from:

[RoutePrefix("api/car")]
public class CarController: ApiController{

    [HTTPGet]
    [Route("")]
    public virtual async Task<ActionResult> GetAll(){

    }

}

So we would .GET("/api/car") and this would throw a 405 error.


The Fix:

The CarController.cs file was in the directory /api/car so when we were requesting this api endpoint, IIS would send back an error because it looked like we were trying to access a virtual directory that we were not allowed to.

Option 1: change / rename the directory the controller is in
Option 2: change the route prefix to something that doesn't match the virtual directory.


check in your project .csproj file and change

<IISUrl>http://localhost:PORT/</IISUrl>

to your website url like this

<IISUrl>http://example.com:applicationName/</IISUrl>

Another possible issue which causes the same behavior is the default parameters in the routing. In my case the controller was located and instantiated correctly, but the POST was blocked because of default Get action specified:

config.Routes.MapHttpRoute(
    name: "GetAllRoute",
    routeTemplate: "api/{controller}.{ext}"/*,
    defaults: new { action = "Get" }*/ // this was causing the issue
);

I was having exactly the same problem. I looked for two hours what was wrong with no luck until I realize my POST method was private instead of public .

Funny now seeing that error message is kind of generic. Hope it helps!


In my case I had a physical folder in the project with the same name as the WebAPI route (ex. sandbox) and only the POST request was intercepted by the static files handler in IIS (obviously).

Getting a misleading 405 error instead of the more expected 404, was the reason it took me long to troubleshoot.

Not easy to fall-into this, but possible. Hope it helps someone.


Make sure your controller inherits from Controller class.

It might even be crazier that stuff would work locally even without that.

참고URL : https://stackoverflow.com/questions/15718741/405-method-not-allowed-web-api

반응형