Search code examples
c#jsonasp.net-core.net-coreasp.net-core-webapi

How to make a PUT request from ASP.NET core mvc to Web API in asp.net core?


I need to save the changes I make in my model through API call in my database. I have checked my API is working fine when I am running it individually on Web. But its giving me an error StatusCode: 405, ReasonPhrase: 'Method Not Allowed'. I am trying to send and object and trying to see whether the request made was completed or not. When I am trying to debug it, it is not sending hit on my API controller.

Here is my model class:

public class Customer
{
    [Required]
    public Guid CustomerId { get; set; }
    public int Age { get; set; }
    public int Phone { get; set; }
}

PUT Method in API:

[HttpPut]
[Route("api/[controller]/{customer}")]
public IActionResult EditCustomer(Customer customer)
{
    var cust = _customerData.EditCustomer(customer);
    if (cust == string.Empty)
    {
        return Ok();
    }
    else
    {
        return new StatusCodeResult(StatusCodes.Status500InternalServerError);
    }
}

The method I am using in project to call API:

using (HttpClient client = new HttpClient())
{
    client.BaseAddress = new Uri(apiBaseUrl);
    client.DefaultRequestHeaders.Accept.Clear();
    client.DefaultRequestHeaders.Accept.Add(
        new System.Net.Http.Headers.MediaTypeWithQualityHeaderValue("application/json")
    );
    var sum = await client.PutAsJsonAsync("api/Customer/", customer);
    if (sum.StatusCode == System.Net.HttpStatusCode.OK)
    {
        return RedirectToActionPermanent(actionName: "SingIn");
    }
    else
    {
        TempData["msg"] = "There is an error";
        return View();
    }

where baseaddress= {https://localhost:44398/}


EditCustomer Method

public string EditCustomer(Customer customer)
{
    try
    {
        var pro = _customerContext.Customer.Where(e => e.CustomerId == customer.CustomerId).FirstOrDefault();
        pro.Age = customer.Age;
        pro.Phone = customer.Phone;
        pro.Name = customer.Name;
        _customerContext.Entry(pro).State = EntityState.Modified;
        _customerContext.SaveChanges();
    }
    catch(Exception e)
    {
        return e.Message;
    }
    return string.Empty;
}

Solution

  • You need to fix your action route by removing {Customer}, since you send customer in request body, not as a route value

     [Route("~/api/Customer")]
    

    and request

      var sum = await client.PutAsJsonAsync("/api/Customer", customer);
    

    or better fix the acttion route name to meaningfull

      [Route("~/api/EditCustomer")]
    

    and

    var sum = await client.PutAsJsonAsync("/api/EditCustomer", customer);
    

    AsJsonAsync sometimes causes problems

    try this code

    var json = JsonSerializer.Serialize(customer);
    //or if you are using Newtonsoft
    var json = JsonConvert.SerializeObject(customer);
    
    var contentData = new StringContent(json, Encoding.UTF8, "application/json");
    var response = await client.PutAsync("/api/Customer", contentData);
                  
    if (response.IsSuccessStatusCode)
        return RedirectToActionPermanent("SingIn");
    else
    {
     TempData["msg"] = "There is an error";
     return View();
    }
    

    but IMHO I would prefer to use

    client.PostAsync("/api/EditCustomer", contentData); 
    

    instead of Put.

    and added [FromBody] to action

     [HttpPost("~/api/EditCustomer")]
     public IActionResult EditCustomer([FromBody] Customer customer)