I've trying to make a request to my aspnet Web Api, with angular, with the $http module inside a factory, like:
http.get('http://localhost:5000/api/todo').success(function(r){ return r; }).error(function(err){ return err; });
But I'm getting the following error:
XMLHttpRequest cannot load http://localhost:5000/api/todo. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin http://localhost:9000/ is therefore not allowed access.
I know that the request arrive to the server because I log a message when I request the resource.
I found that I had to implement CORS at the server. I added the CORS middleware and configure my Startup file, but nothing changed.
I suppose that the middleware should add the configured headers to the response, but It doesn't.
¿What is the problem in this context?
Ok, after a small research. I found that .WithOrigins("...") method is not adding the Access-Control-Allow-Origin header, I don't know if it's the context or what, I just made an issue about it. I replace it with .AllowAnyOrigin() by now.
And also added an attribute to my controller class.
[EnableCorsAttribute("AllowAll")]
Of course you need to add the namespace where EnableCorsAttribute class is.
using Microsoft.AspNet.Cors.Core;
This worked for me I hope it help you, thanks for the comments.
Related
Forgive me for the obvious error I am obviously committing...
I understand CORS, how and why it's used. But I'm missing the blindingly obvious in this instance.
I'm trying to access a publicly available API that should work fine (I've been assured)
If I hit the endpoint in Chrome, or in Postman, all works fine: wonderful JSON is returned.
When I try to do the same using axios from within my create-react-app's componentDidMount, I get a CORS error, specifically
Access to XMLHttpRequest at 'http://some-interesting-url/sub-url?blabla=blip&foo=bar' from origin 'http://localhost:3000' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.
What is it I'm failing to grasp? Is there anything I can do from my end? (I have no control over the server)
The Postman app is not a browser so it isn't bound by the rules of CORS. In a browser too, trying to access a URL directly doesn't trigger Cross-Origin-Request-Sharing policies. CORS, by definition will only affects the 'cross-origin' requests made from background JS code of a web-page, to another web-page or API not hosted on same domain name.
Based on the error posted, the API in question is not sending Access-Control-Allow-Origin header. If it's possible to get the API changed, that you should get the header added to response (with value '*', or your domain name). However if that's not possible, then you'd need to route the request through a web-server that you own and include this header there. This kind of does work like a proxy, albeit for a specialized use-case.
If you already have some server side application running, you can simply add another end point to your application. A call to this new end point should trigger the 'Public API' call, and send the response back to client. Since the server side program (eg PHP/Python/NodeJS) would never be a browser, they will not face the CORS issues. If your original web-page is also loaded from same web-server, then the response header can be skipped.
I have an AngularJs website and when I am trying to post data then when I am opening my website without using www then I am getting
Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource
Otherwise, I am not getting any error.
I tried to search and found that I should implement CORS on my backend which is in NodeJs but can anyone please tell me how can I only implement CORS Headers such that for both www and without, it would work but for any other domain trying to access my API must result in preflight error.
I am trying to do this because I read here which-security-risks-do-cors-imply that allowing all domains can increase security overhead for my website which I do not want.
Thanks.
I'm afraid this is not something you can tweak just in your client-side code. In order for cross-origin requests to work, you need to set an http response header: it's the server, who serves the resource, who will need the change, not the client side code from angularJs.
I believe that you should update your question stating what your server side language is and how are you handling http requests in the server side. As far as I know, just adding a header like:
Access-Control-Allow-Origin: http://client.domain.com
In your responses will do the trick. Where client.domain.com is the domain of your client, angularJs application.
i'm a frontend developer.
i want to get metadata.
so i use the metascraper libraray. ==>https://www.npmjs.com/package/metascraper
it is npm libraray.
but i'm faced with an unexpected difficulty that cors error.
how can i do?
please help me.
Metascraper
.scrapeUrl("http://www.naver.com")
.then((metadata) => {
console.log(metadata)
})
As you don't control the target, the only solution is to proxy the request through your local server.
To do that, you'd create a server side script in something like PHP/Node which takes a URL and does a server-to-server request to get the response and output it. Your Metascraper would call your local server side script, passing the target URL. This would work because server-to-server calls are not subject to CORS.
If you did happen to control the target, then you can output a CORS header (access-control-allow-origin) to disable CORS for everyone or a whitelist of domains.
Could you share the error, that you get in console browser?
I have tried to do the same request to naver.com.
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script>
$(function(){
$.get('https://www.naver.com/').then(function(response) {
console.log(response);
});
})
</script>
And got the next error:
XMLHttpRequest cannot load https://www.naver.com/. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:9080' is therefore not allowed access.
So we can make a conclusion that naver.com server doesn't support CORS.
And there is no problem with library that you are trying to use.
This route works, and works nicely using SoapUI:
from("restlet:http://localhost:8484/restletTestService/submit?restletMethod=POST")
.routeId("myRestletSubmitRoute")
.unmarshal().json(JsonLibrary.Jackson, MyRequest.class)
.to("bean:myServiceSubmitProcessor")
.marshal().json(JsonLibrary.Jackson, MyResponse.class);
Using SoapUI, I can post jsons that conform to the structure of the MyRequest class and I get a json back with the info I think I should.
However, when I created a quick angularjs page to allow users to build a request on the fly and then 'POST' to my rest endpoint, well:
XMLHttpRequest cannot load http://localhost:8484/restletAddressService/addressPersonator/submit. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://localhost:8080' is therefore not allowed access. The response had HTTP status code 405.
I'm pretty sure that I have to somehow set the header Access-Control-Allow-Origin to some value on the restlet URI, but I haven't a clue how to do that. I researched the documentation (http://camel.apache.org/restlet.html) and googled it, but I'm not finding anything that has helped.
Does anyone know the answer? Thanks!
UPDATE
So the answer from fiw gave me the hint I needed along with some google research on HOW a call to a rest resource determines what's allowed (plus quite a bit of good-ole-fashioned trial and error :) ). This is what wound up working:
from("restlet:http://localhost:8484/restletTestService/submit?restletMethod=POST")
.routeId("myRestletSubmitRoutePOST")
.unmarshal().json(JsonLibrary.Jackson, MyRequest.class)
.to("bean:myServiceSubmitProcessor")
.marshal().json(JsonLibrary.Jackson, MyResponse.class)
.setHeader("Access-Control-Allow-Headers", constant("Content-Type"))
.setHeader("Access-Control-Allow-Origin", constant("*"));
from("restlet:http://localhost:8484/restletTestService/submit?restletMethod=OPTIONS")
.routeId("myRestletSubmitRouteOPTIONS")
.setHeader("Access-Control-Allow-Headers", constant("Content-Type"))
.setHeader("Access-Control-Allow-Origin", constant("*"));
Thanks!
I think you need to set Access-Control-Allow-Origin as a header on the response with a value of * as you've suggested. So to do this in camel:
from("restlet:http://localhost:8484/restletTestService/submit?restletMethod=POST")
.routeId("myRestletSubmitRoute")
.unmarshal().json(JsonLibrary.Jackson, MyRequest.class)
.to("bean:myServiceSubmitProcessor")
.marshal().json(JsonLibrary.Jackson, MyResponse.class)
.setHeader("Access-Control-Allow-Origin", constant("*"));
This came from reading: enable cors on your server.
How can we perform cross site ajax request from angular js? I have tried doing in this way:
$http.post('http://cross.local', data)
But the browser is throwing an error:
No 'Access-Control-Allow-Origin' header is present on the requested
resource. Origin is therefore not allowed access.
So i added the headers
Access-Control-Allow-Credentials:true
Access-Control-Allow-Methods:GET,POST,DELETE,OPTIONS
Access-Control-Allow-Origin:*
But I'm still getting the same error.
Where did I go wrong?
You need to enable the CORS support in Angular, which is off by default
yourApp.config(['$httpProvider', function($httpProvider) {
$httpProvider.defaults.useXDomain = true;
delete $httpProvider.defaults.headers.common['X-Requested-With'];
}
]);
The first line enables the CORS support, the second removes the header that typically is send with Ajax requests.
If you do not want this behavior everywhere in your app, you need to fine tune where to set the defaults.
In the server i forget to add the handler for POST request, So for each post request 'No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin is therefore not allowed access.' error is thrown by the server. When i added the POST handler it worked