Action routing in .Net Core 3 Web API - c#

I am busy migrating an existing-working WebApi from .Net Core 2.2 to 3, however, the routing stopped working. I keep getting a 404 Not Found message.
Would like to use the action names as part of the route template in my controller, for example:
[Route("/api/[controller]/[action]")]
Call example: /api/Lookup/GetBranchesAsync
I'm just really confused about why it stopped working.
Please see the code below.
Startup:
public class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.AddScoped<IAuthService, AuthService>();
services.AddScoped<ILookupService, LookupService>();
services.AddScoped<IFranchiseRepo, FranchiseRepo>();
services.AddScoped<ILogRepo, LogRepo>();
services.AddSingleton<IConfiguration>(Configuration);
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseHttpsRedirection();
app.UseRouting();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}
Controller:
[ApiController]
[Route("/api/[controller]/[action]")]
[Produces("application/json")]
public class LookupController : Controller
{
private readonly ILookupService lookupService;
public LookupController(ILookupService lookupService)
{
this.lookupService = lookupService;
}
[HttpGet]
public async Task<IActionResult> GetBranchesAsync()
{
}
[HttpGet("{branchID}")]
public async Task<IActionResult> GetBranchSEAsync(int? branchID)
{
}
}
Any advice on what the issue could be?

According to https://github.com/aspnet/AspNetCore/issues/8998, in .NET Core 3.0 Async is skipped by default in Action name. Your endpoint is available at /api/Lookup/GetBranches. You can change this behaviour by replacing
services.AddControllers();
with
services.AddControllers(options => options.SuppressAsyncSuffixInActionNames = false);
in ConfigureServices method, or just use the new routes

Related

-Authorize- not working with 2 ASP.NET MVC controllers

I'm building an ASP.NET MVC web app with 2 controller, 1 that send requests to an API and the other one that will handle authentication. The app build just fine but the authorize tag is not working, I can easily access the secret page without having the cookie.
This is the Access controller:
public class AccessController : Controller
{
public IActionResult Index()
{
return View();
}
public IActionResult Login()
{
return RedirectToAction("Index");
}
[Authorize]
public IActionResult Secret()
{
return View();
}
}
And this is the startup.cs file:
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
//services.AddControllers();
// Add session
services.AddDistributedMemoryCache();
services.AddSession();
// Add services to the container.
services.AddSingleton<IClient, ClientConcessionario>();
services.AddAuthentication("CookieAuth").AddCookie("CookieAuth", config =>
{
config.Cookie.Name = "CookieAuth";
config.LoginPath = "/Access/Login";
});
services.AddControllersWithViews();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseSession();
app.UseRouting();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapDefaultControllerRoute();
});
;
}
}
I can views all the urls of both the controllers, but I shouldn't be able to access the secret page without a cookie. Any clue?
You should call UseAuthentication() and UseAuthorization() in Configure method BEFORE UseRouting.

ASP.Net Core "This localhost page can’t be found" HTTP ERROR 404

When I want to run my project with .Net Core MVC architecture with Visual Studio 2019 program on my Mac, I get the error "This localhost page can't be found". I am sharing Startup.cs and controller classes.
I am working with .NetCore version 3.1.
Thanks in advance.
namespace Test
{
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.AddSingleton<VendorRegistrationService>();
services.AddCors(o => o.AddPolicy("ReactPolicy", builder =>
{
builder.AllowAnyOrigin()
.AllowAnyMethod()
.AllowAnyHeader();
//.AllowCredentials();
}));
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseHttpsRedirection();
app.UseRouting();
app.UseCors("ReactPolicy");
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}
}
VendorRegistrationController.cs
namespace Test.Controllers
{
[Produces("application/json")]
[Route("api/[controller]")]
[ApiController]
[EnableCors("ReactPolicy")]
public class VendorRegistrationController : ControllerBase
{
public readonly VendorRegistrationService vendorRegistrationService;
public VendorRegistrationController(VendorRegistrationService vendorRegistrationService)
{
this.vendorRegistrationService = vendorRegistrationService;
}
[HttpPost]
public IActionResult Post([FromBody] VendorRegistration vendorRegistration)
{
return CreatedAtAction("Get", vendorRegistrationService.Create(vendorRegistration));
}
}
}
Is this a web api project?
Check this configuration of yours:
"profiles": {
"IIS Express": {
"commandName": "IISExpress",
"launchBrowser": true,
"launchUrl": "api/home/test",
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
}
},
If your launchUrl is not given a default url or given a wrong route, the above error will occur, and the default launch path cannot be found. You can add what you need, such as:
Controller
namespace WebApplication130.Controllers
{
[ApiController]
[Route("api/[controller]")]
public class HomeController : Controller
{
[Route("test")]
public string Index()
{
return "sucess!";
}
}
}
Result:
In my case I was running the sample project at:
https://learn.microsoft.com/en-us/training/modules/build-web-api-aspnet-core/3-exercise-create-web-api
using:
dotnet new webapi -f net6.0
and I forgot to include the weatherforecast route on the url:
https://localhost:{PORT}/weatherforecast

Cors implementation in .Net Core 3.1 project with Oracle Database Host

Only one HOST can connect to the API, in this case it is an Oracle server.
I added Cors as per Microsoft docs, still other HOST can connect to my API. Has anyone tried to add an Oracle Database HOST? Is there something wrong with the configuration?
Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.AddHttpClient();
services.AddCors(options =>
{
options.AddPolicy(name: "CorsPolicy",
builder =>
{
builder.WithOrigins("http://oraas1111.net:1001")
.AllowAnyHeader()
.AllowAnyMethod();
});
});
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseRouting();
app.UseCors("CorsPolicy");
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers().RequireCors("CorsPolicy");
});
}
Controller.cs
[EnableCors("CorsPolicy")]
[Route("[controller]")]
[ApiController]
public class Controller : ControllerBase
{
[HttpPost]
[Route("/Service/[action]")]
public async Task<ActionResult<Request>> Update(Request data)
{
}
[HttpGet]
[Route("/GET_Service/[action]")]
public ActionResult Test()
{
return Ok();
}
}
You have to move services.AddCors() to the top, before AddControllers()

Configure IdentityServerJwt Authentication with Authorization

I have an Blazor webassembly application which uses IdentityServerJwt AddAuthentication and is working with Hangfire. I am trying to configure Hangfire to allow only users who are admins authorization based on the article here but I am getting an No authentication handler is registered for the scheme 'Bearer' error. What should I add as an AuthenticationSchemes. JwtBearerDefaults.AuthenticationScheme` does not work.
What am I missing?
public partial class Startup
{
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
string handfirepolicyname="HangfirePolicyName";
public void ConfigureServices(IServiceCollection services)
{
...Code removed for brevity
services.AddAuthentication().AddIdentityServerJwt();
services.AddAuthorization(options =>
{
options.AddPolicy(handfirepolicyname, builder =>
{ builder.AddAuthenticationSchemes(JwtBearerDefaults.AuthenticationScheme).RequireAuthenticatedUser();
builder.RequireRole("admin");
});
});
var hangfireConnectionstring = "SomeHangfireDatabaseConnectionString";
var mySqlStorageOptions = new MySqlStorageOptions();
var mySqlStorage = new MySqlStorage(hangfireConnectionstring, mySqlStorageOptions);
services.AddHangfire(config => config.UseStorage(mySqlStorage));
services.AddHangfireServer();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env, ApplicationIdentityDbContext identityDbContext)
{
...Code removed for brevity
app.UseIdentityServer();
app.UseAuthentication();
app.UseAuthorization();
//UseAuthentication, UseAuthorization should be before UseHangfireDashboard
app.UseHangfireDashboard();
app.UseEndpoints(endpoints =>
{
endpoints.MapHangfireDashboard("/hangfire", new DashboardOptions()
{
Authorization = new List<IDashboardAuthorizationFilter> { }
}).RequireAuthorization(handfirepolicyname);
});
}
Error:
No authentication handler is registered for the scheme 'Bearer'. The registered schemes are: Identity.Application, Identity.External, Identity.TwoFactorRememberMe, Identity.TwoFactorUserId, idsrv, idsrv.external, IdentityServerJwt, IdentityServerJwtBearer. Did you forget to call AddAuthentication().Add[SomeAuthHandler]("Bearer",...)?
by adding
[Authorize(AuthenticationSchemes = "Bearer")]
public class TestController : ControllerBase{}
on top of the controller

issue with post(create a record) webapi in blazor server app

I create a blazor server app project and I am using built in webapi framework
I am checking a create record webapi in postman but it give a 204 content means my webapi run but it return 204 content see below image
//webapi test in postman but it return 204 content
blazor server app
EmpsController.cs
namespace CrudBlazorServerApp.Controllers
{
[Route("api/[controller]")]
[ApiController]
public class EmpsController : ControllerBase
{
private readonly sqldbcontext _context;
public EmpsController(sqldbcontext context)
{
_context = context;
}
// GET: api/Emps
[HttpGet]
public async Task<ActionResult<IEnumerable<Emp>>> Getemps()
{
return await _context.emps.ToListAsync();
}
// GET: api/Emps/5
[HttpGet("{id}")]
public async Task<ActionResult<Emp>> GetEmp(int id)
{
var emp = await _context.emps.FindAsync(id);
if (emp == null)
{
return NotFound();
}
return emp;
}
[HttpPost]
public async Task<ActionResult<Emp>> PostEmp(Emp emp) //here I am facing issue record is not created
{
_context.emps.Add(emp);
await _context.SaveChangesAsync();
return CreatedAtAction("GetEmp", new { id = emp.empid }, emp);
}
Startup.cs
namespace CrudBlazorServerApp
{
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.
// For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
public void ConfigureServices(IServiceCollection services)
{
services.AddCors();
services.AddControllers()
.AddJsonOptions(options => options.JsonSerializerOptions.IgnoreNullValues = true);
services.AddDbContext<sqldbcontext>(options => options.UseSqlServer(Configuration.GetConnectionString("sqlserverconnn")));
services.AddRazorPages();
services.AddServerSideBlazor();
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
using (var serviceScope = app.ApplicationServices.GetService<IServiceScopeFactory>().CreateScope())
{
var context = serviceScope.ServiceProvider.GetRequiredService<sqldbcontext>();
context.Database.EnsureCreated();
}
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
// The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
app.UseHsts();
}
app.UseCors(policy =>
policy.WithOrigins("https://localhost:44399") // client address
.AllowAnyMethod()
.WithHeaders(HeaderNames.ContentType));
app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
endpoints.MapBlazorHub();
endpoints.MapFallbackToPage("/_Host");
});
}
}
}
why it give 204 no content?
.net core project version : netcoreapp3.1
what I am trying:
I comment this line
await _context.SaveChangesAsync();
but record not created
please help
which place need to correction?

Categories

Resources