Browser security prevents a web page located on a domain to make requests to a web page which is located on a different domain. This restriction is called the same-origin policy.
For example suppose I have a web page called A.html in my website. It’s URL being:
https://www.yogihosting.com/A.html
Now page A.html has an AJAX code that tries to read the HTML source code of another page B.html, but B.html is located on a different domain with it’s URL as:
http://www.asp.net/B.html
The AJAX call will return the error message:
No ‘Access-Control-Allow-Origin’ header is present on the requested resource.Thankfully there is Cross Origin Resource Sharing (CORS) which is a W3C standard that allows browsers to relax the same-origin policy.
So if the website asp.net implements CORS then my website’s page called A.html will be able to make successful AJAX request to B.html and can get B’s HTML source code by using AJAX.Many times, this value will be *
, meaning that Server will share the requested resources with any domain on the Internet. Other times, the value of this header may be set to a particular domain (or list of domains), meaning that Server will share its resources with that specific domain (or list of domains).
And in this way CORS works to relax the same-origin policy.
PM> Install-package Microsoft.AspNetCore.Cors
public void ConfigureServices(IServiceCollection services)
{
services.AddCors();
services.AddControllersWithViews();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Home/Error");
app.UseHsts();
}
app.UseHttpsRedirection();
// Shows UseCors with CorsPolicyBuilder.
app.UseCors(builder =>
{
builder
.AllowAnyOrigin()
.AllowAnyMethod()
.AllowAnyHeader();
});
app.UseStaticFiles();
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
});
}
app.UseCors(builder =>
{
builder
.AllowAnyOrigin()
.AllowAnyMethod()
.AllowAnyHeader();
});
I have also used other method which are described below:
If you want to enable CORS for request made from 1 domain only like https://www.yogihosting.com then change the above code to:
app.UseCors(builder =>
{
builder
.WithOrigins("https://www.yogihosting.com")
.AllowAnyMethod()
.AllowAnyHeader()
.AllowCredentials();
});
You can specify more than 1 domains like this:
app.UseCors(builder =>
{
builder
.WithOrigins(new string[] { "https://www.yogihosting.com", "https://example1.com", "https://example2.com" })
.AllowAnyMethod()
.AllowAnyHeader()
.AllowCredentials();
});
Define one or more named CORS policies and select the policy by name at runtime. See the following example which adds a user-defined CORS policy named as MyPolicy.
To select the policy, pass the name to the UseCors() method:public void ConfigureServices(IServiceCollection services)
{
services.AddCors(options =>
{
options.AddPolicy("MyPolicy",
builder => builder.WithOrigins("https://www.yogihosting.com"));
});
services.AddControllersWithViews();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Home/Error");
app.UseHsts();
}
app.UseHttpsRedirection();
// Shows UseCors with named policy.
app.UseCors("MyPolicy");
app.UseStaticFiles();
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
});
}
Now you can apply this CORS policy per action or per controller.
[EnableCors("MyPolicy")]
public IEnumerable<string> Get()
{
return new string[] { "value1", "value2" };
}
[EnableCors("MyPolicy")]
public class HomeController : Controller
[DisableCors]
public string Get(int id)
{
return "value";
}
The link to download the full source code of this tutorial is given below:
I hope you loved this tutorial on CORS in ASP.NET Core. Please share it on your Facebook and Twitter accounts. Also check my other related tutorial given in the below section.
Good article thanks.
One thing I haven’t seen anywhere yet, how can we implement more than one policy i.e. within a controller specifying one of two policies per route.
For example, all POST PATCH and DELETE methods are for an Admin site.
GET method is for a Public site, except one endpoint which needs to support POST (to add a comment).
How would you configure .Net for that scenario?
We can add multiple policies and apply them to action methods of controllers as attributes.