Search code examples
javascriptc#jsonasp.net-web-apitoken

Fetch fail with ERROR : POST 415 & GET 405


I tried to modify this Microsoft.docs Sample => Call an ASP.NET Core web API with JavaScript
I want to use fetch POST to send username and password,and my AccountController should return Token
Before doing this , I already tested my login API on POSTMAN & Swagger, it works!
UPDATE
I resolve the POST ERROR 415, but still have GET ERROR 405,can somebody tell me the reason? Thanks!

My Error : Imgur
My Testing:

{
  "username": "Genevieve",
  "password": "sss"
}
Curl

curl -X POST "https://localhost:5001/login" -H  "accept: text/plain" -H  "Content-Type: application/json" -d "{\"username\":\"Genevieve\",\"password\":\"string\"}"
Request URL https://localhost:5001/login

Server response
Code    Details
200 
Response body
Download
{
  "token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiJHZW5ldmlldmUiLCJqdGkiOiJmYjJhNjdlNC1hZWFjLTRkMTktOWU2ZC03NDk0ZTVmMWYwNzciLCJyb2xlcyI6IkFkbWluIiwibmJmIjoxNjI4ODM0NTcwLCJleHAiOjE2Mjg4MzgxNzAsImlhdCI6MTYyODgzNDU3MCwiaXNzIjoiYXBpMSJ9.8HqCMwAbm3KXMXTGo868dARfF1UfMC1BEniq01UfyFQ"
}
Response headers
 content-type: application/json; charset=utf-8 
 date: Fri13 Aug 2021 06:02:49 GMT 
 server: Kestrel 

My Javascript Code :

function sendtoken(){
    const token_name = document.getElementById('token_name');
    const data = {
        username : 'Genevieve',
        password : 'sss'
    };
    fetch('login', {
        method: 'POST',
        headers: {
            'Accept' : 'application/json, text/plain, */*',
            'Content-Type': 'application/json'
        },
        body : JSON.stringify(data)
    })
    .then(response => response.json())
    .then(() => {
        getToken();
    })
    .catch( error => console.error('Unable to send Token.', error));
}

function getToken(){
    fetch('login')
    .then(response => response.json())
    .then( data => _displayToken(data))
    .catch( error => console.error('Unable to get Token.', error));
}

function _displayToken(data){
    const final = document.getElementById('Token');
    final.innerHTML = data.token ;
    console.log(data.token);
}

My API :

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using api1.Helpers;
using api1.Models;
using api1.ViewModels;
using Microsoft.AspNetCore.Cors;

namespace api1.Controllers
{
    [ApiController]
    public class AccountController : ControllerBase
    {
        private readonly JwtHelpers helpers;

        public AccountController(JwtHelpers helpers)
        {
            this.helpers = helpers;
        }
        [EnableCors("GetPolicy")]
        [HttpPost("login")]
        public ActionResult<LoginResult> Login(Login model)
        {
            if (CheckPassword(model.Username,model.Password))
            {
                return new LoginResult(){
                    Token = helpers.GenerateToken(model.Username,"Admin",60)
                };
            }
            else
            {
                return BadRequest();
            }
        }

        private bool CheckPassword(string username, string password)
        {
            if(username == "Genevieve")
            {
                return true;
            }
            else
            {
                return false;
            }
        }
    }
}

Solution

  • fetch('login', {
        method: 'POST',
        headers: {
            'Accept' : 'application/json, text/plain, */*',
            'Content-Type': 'applicaiotn/json'
        },
        body : JSON.stringify(data)
    

    As you can see in your code, you wrote 'applicaiotn/json', which is not spelled right. It makes sense you got a 415 (unsupported media) because 'applicaiotn/json' is not supported. Fix your spelling errors.

    The 405(Method not allowed) is because you don't have an endpoint at '/login' that supports HTTP GET(a method type). You need to add another method/endpoint that has [HttpGet("login")] on it.

    This is what you are looking for I think

        fetch('login', {
            method: 'POST',
            headers: {
                'Accept' : 'application/json, text/plain, */*',
                'Content-Type': 'application/json'
            },
            body : JSON.stringify(data)
        })
        .then(response => response.json()
            .then( data => _displayToken(data)
          .catch( error => console.error('Unable to get Token.', error))))
       .catch( error => console.error('Unable to send Token.', error));