Веб-Api Игнорирует Атрибут Маршрута

#c# #api #web #webapi

#c# #API #сеть #webapi

Вопрос:

Я работаю над проектом веб-API, и когда я запускаю его и пытаюсь использовать маршрут для контроллера, он не работает, а вместо этого выдает ошибку 404. Почему веб — API игнорирует атрибут маршрута?

Я оставлю код ниже:

 [ApiController] [Route("api/[controller]")]  public class Controller3 : ControllerBase {  private readonly IServiceContract3 _interest;  public Controller3(IServiceContract3 interest)  {  _interest = interest;  }   [HttpGet]  [Route("[action]")]  [Route("api/Interest/GetInterests")]  public IEnumerablelt;Interestgt; GetEmployees()  {  return _interest.GetInterests();  }   [HttpPost]  [Route("[action]")]  [Route("api/Interest/AddInterest")]  public IActionResult AddInterest(Interest interest)  {  _interest.AddInterest(interest);  return Ok();  }   [HttpPost]  [Route("[action]")]  [Route("api/Interest/UpdateInterest")]  public IActionResult UpdateInterest(Interest interest)  {  _interest.UpdateInterest(interest);  return Ok();  }   [HttpDelete]  [Route("[action]")]  [Route("api/Interest/DeleteInterest")]  public IActionResult DeleteInterest(int id)  {  var existingInterest = _interest.GetInterest(id);  if (existingInterest != null)  {  _interest.DeleteInterest(existingInterest.Id);  return Ok();  }  return NotFound($"Employee Not Found with ID : {existingInterest.Id}");  }   [HttpGet]  [Route("GetInterest")]  public Interest GetInterest(int id)  {  return _interest.GetInterest(id);  }  }  

И для моего стартапа.cs

 public class Startup {  public Startup(IConfiguration configuration)  {  Configuration = configuration;  }   public IConfiguration Configuration { get; }   // This method gets called by the runtime. Use this method to add services to the container.  public void ConfigureServices(IServiceCollection services)  {  services.AddControllers();  services.AddDbContextPoollt;DatabaseContextgt;(options =gt;  options.UseSqlServer(Configuration.GetConnectionString("DB")));  }   // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.  public void Configure(IApplicationBuilder app, IWebHostEnvironment env, DatabaseContext context)  {  if (env.IsDevelopment())  {  app.UseDeveloperExceptionPage();  }   context.Database.Migrate();   app.UseHttpsRedirection();   app.UseRouting();   app.UseAuthorization();   app.UseEndpoints(endpoints =gt;  {  endpoints.MapControllers();  });  } }  

Как я могу исправить маршрутизацию? Каждый раз, когда я пытаюсь сделать это в своем браузере, например https://localhost:44316/api/Interest/GetInterests Вместо этого я получаю ошибку 404. Почему это происходит?

Комментарии:

1. Что произойдет, когда вы вместо этого отправитесь по указанному http адресу?

2. Где IServiceContract3 регистрируется для внедрения зависимостей?

Ответ №1:

Обычно контроллеры для webapi определяются следующим образом:

 [ApiController] [Route("api/[controller]")] public sealed class InterestController : ControllerBase {  private readonly IServiceContract3 _interest;   public InterestController(IServiceContract3 interest)  {  _interest = interest;  }   [HttpGet, Route("GetInterests")]  public IActionResult GetEmployees()  {  // this is located at: GET api/Interest/GetInterests  return Ok(_interest.GetInterests());  }    [HttpPost, Route("AddInterest")]  public IActionResult AddInterest([FromBody] Interest interest)  {  // this is located at: POST api/Interest/AddInterest  }   [HttpPost, Route("UpdateInterest")]  public IActionResult UpdateInterest([FromBody] Interest interest)  {  // this is located at: POST api/Interest/UpdateInterest  }   [HttpDelete, Route("DeleteInterest/{id}")]  public IActionResult DeleteInterest([FromRoute] int id)  {  // this is located at: DELETE api/Interest/DeleteInterest/{id}  }   [HttpGet, Route("GetInterest/{id}")]  public IActionResult GetInterest([FromRoute] int id)  {  // this is located at: GET api/Interest/GetInterest/{id}  return Ok(_interest.GetInterest(id));  } }  

Во-первых, вы хотите назвать свой контроллер соответствующим именем, которое будет распространяться на всю остальную часть вашего контроллера. Итак, это дело, на которое я перешел Controller3 InterestController . Поскольку маршрут контроллера таков "/api/[Controller]" , он будет переведен в "api/Interest" .

Затем удалите [Action] атрибуты. В этом сценарии они вам не нужны.

Затем убедитесь, что ваши маршруты верны. Если вы передаете идентификатор, определите свой идентификатор в маршруте, используя {id} и установив [FromRoute] атрибут для ясности. Кроме того, используйте [FromBody] для определения параметров, которые будут исходить от тела. Многие из них являются «стандартными» (то есть вам не нужно их добавлять), но это помогает с ясностью.

Наконец, если вы используете IActionResult шаблон, придерживайтесь его через свой контроллер. Не смешивайте/не сопоставляйте типы возвращаемых данных между конечными точками, потому что это сбивает с толку при обслуживании.

И последнее: имена конечных точек вашего контроллера немного избыточны. Например, вы могли бы сделать это:

 [HttpGet, Route("")]  public IActionResult GetEmployees()  {  // this is located at: GET api/Interest  return Ok(_interest.GetInterests());  }    [HttpPut, Route("")]  public IActionResult AddInterest([FromBody] Interest interest)  {  // this is located at: PUT api/Interest/  }   [HttpPost, Route("")]  public IActionResult UpdateInterest([FromBody] Interest interest)  {  // this is located at: POST api/Interest/  }   [HttpDelete, Route("{id}")]  public IActionResult DeleteInterest([FromRoute] int id)  {  // this is located at: DELETE api/Interest/{id}  }   [HttpGet, Route("{id}")]  public IActionResult GetInterest([FromRoute] int id)  {  // this is located at: GET api/Interest/{id}  return Ok(_interest.GetInterest(id));  }  

т. е.: Используйте «HTTP-глагол» в своих интересах для разделения действий.

Ответ №2:

вы должны исправить свой маршрут, сделав api корневым. Замените «api» на «~/api». ИМХО, вы должны удалить [действие] из действий и добавить его в контроллер. Также исправьте имя контроллера

 [ApiController]  [Route("~/api/[controller]/[action]")]  public class InterestController : ControllerBase   [HttpGet("~/api/Interest/GetInterests")]  public IEnumerablelt;Interestgt; GetEmployees()  ....     [HttpPost("~/api/Interest/AddInterest")]  public IActionResult AddInterest(Interest interest)  ...     [HttpPost("~/api/Interest/UpdateInterest")]  public IActionResult UpdateInterest(Interest interest)  ...     [HttpDelete("~/api/Interest/DeleteInterest/{id}")]  public IActionResult DeleteInterest(int id)  ....   [HttpGet("~/api/Interest/GetInterest/{id}")]  public Interest GetInterest(int id)