CORS issue with Rackspace CloudFiles - angularjs

I have an Angular 1.x application using the popular ng-file-upload to make a request to the Rackspace OpenCloud library for uploading files to a CDN.
In a nutshell the script below - uploads a file, sends it to the backend of the application & in turn sends a request to the Rackspace Container and returns the public URL. This all works fine in Postman without issues - when I implement this into my Angular application I have some issues with CORS (see upload code below) - the frontend Angular sends a request to our backend app which in turn sends a request to the OpenCloud to upload a file to the Rackspace CDN and returns the public URL.
// frontend Angular app
Upload.upload({
url : 'https://asite.com/users/request',
data : {
__token : $localStorage.token.value,
fileToUpload : file
}
// additional code below not shown for clarity
In the console log I see the following : ( I have the changed the actual url below for security purposes) :-
Failed to load https://xxxxxxxxxxxxxx-2426685a61633353dfd5b28cdbf2b449.ssl.cf3.rackcdn.com/5a7d6de352a949.48129019.pdf: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://domain.local' is therefore not allowed access. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
How do I prevent this CORS error so it loads the file from the CDN?

fixed - the issue was actually on the PHP backend (in case it helps out somebody else)
$object = $container->DataObject();
$object->Create(array(
'name' => $filename,
'content_type' => $mime,
'extra_headers' => array('Access-Control-Allow-Origin' => '*'
)), $file);
I needed to add this in the extra headers array when creating the file using the OpenCloud SDK

Related

Enable CORS in an Angular Paypal Docker application

My application with angular front end and springboot backend is trying to make a REST POST call to one of the PayPal APIs from Angular front end. The application is deployed as a Docker container in GCP VM instance. If I dont open the broser with web security disabled I get the ERROR
"Access to XMLHttpRequest at 'https://pilot-payflowpro.paypal.com/' from origin 'http://myserverip' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource."
I see lot of answers for this question in SO and others with adding headers in httpd.conf / .htaccess files. But I dont have both these files. I tried adding headers to Dockerfile and also adding commands to docker-compose.yaml file. Also tried adding the end URL in angular proxy configuration file. None of it worked.
Is there any way to enable CORS either in a docker config file or in the server itself.
docker-compose.yml
image: docker.image.link
privileged: true
ports:
- '80:8080'
restart: 'no'
volumes:
- '/var/sftp/upload:/usr/share/invoice/invoiceFile'
environment:
- SPRING_PROFILES_ACTIVE=docker
- DB_CONN_STRING=jdbc:postgresql:url
- DB_USER=postgres
- DB_PASS=postgres
- HOST_NAME=hostname
- SMTP_HOST=smtphost
- SMTP_PORT=25
- SMTP_AUTH_TRUE_FALSE=false
Dockerfile
FROM openjdk:8-jdk-alpine
ARG JAR_FILE
ADD target/${JAR_FILE} /usr/share/application.jar
ADD template/ /usr/share/template
VOLUME /tmp
EXPOSE 8080
ENTRYPOINT ["java", "-jar", "/usr/share/application.jar"]
The CORS error is an error emitted by the browser when the request response, from the backend, hasn't the properly headers to tell to the browser that this client can perform/view the request.
So, in your case the backend is the PayPal (https://pilot-payflowpro.paypal.com/ -> paypal.com) not your backend, so even if you add any headers to your backend or frontend, the problem will persist because the only header that is important when you perform the request to the https://pilot-payflowpro.paypal.com/ is the header from the response of this request.
To solve this problem the https://pilot-payflowpro.paypal.com/ needs to send the correct header response allowing you to perform this request, and I think it's not possible because security reasons.
Some endpoints can't be use from a frontend application, only from a backend, and I think it's your case.
To avoid the CORS problem you can create an endpoint in your backend that call the https://pilot-payflowpro.paypal.com/. So, in your frontend you call your backend endpoint and the backend call the PayPal API.
calling the REST call is one solution. Another solution would be to mask the endpoint URL in the proxy configuration in Angular.
"/paypal" : {
"target" : "https://pilot-payflowpro.paypal.com/",
"secure" : true,
"changeOrigin": true,
"pathRewrite":{
"^/paypal":""
}
}
And calling /paypal where we have to do the REST call.

Access-Control-Allow-Origin Error Only on a Single Route, Only When Deployed to GAE

I'm using google app engine to host both my frontend and my api backend. I'm getting the following errors when I'm polling the "slicingdone" route on my backend:
bootstrap e65cef5bb029055e1719:2 GET
https://playloopsbackend-217106.appspot.com/playloops/slicingdone 502
send # bootstrap e65cef5bb029055e1719:2
/videotogifs:1 Access to XMLHttpRequest at
'https://playloopsbackend-217106.appspot.com/playloops/slicingdone'
from origin 'https://playloopsfrontend.appspot.com' has been blocked
by CORS policy: No 'Access-Control-Allow-Origin' header is present on
the requested resource.
I poll the slicingdone function to figure out when trimming of a video on my backend is finished. It works locally but is presenting the above errors when deployed to gcloud.
slicingdone function on my backend looks like this(Express):
slicingdone(req, res, next) {
if(slicingIsDone == true){
res.status(200).send('true');
slicingIsDone = false;
}else{
res.status(200).send('false');
}
}
*Every other route on my backend works fine even when deployed. I have similar functions on the backend that manipulate videos using ffmpeg in different ways. I have whitelisted my frontend url on my backend, so I'm not sure why I'm getting these CORs errors. I store the video results in google cloud storage--perhaps I need to add my backend url to google cloud CORS whitelist?
Any help is much appreciated! Thank you!

On Ionic 2, XMLHttpRequest cannot load .. with Laravel api

This is my scenario:
XMLHttpRequest cannot load http://phi.dev/api/login. Redirect from 'http://phi.dev/api/login' to 'http://localhost:8100/' has been blocked by CORS policy: Request requires preflight, which is disallowed to follow cross-origin redirect.
I have a Aungular2/Ionic 2 App on local and a Laravel Web API for authenticating user.
if I call this Web API from my Angular2 Module, I get an exception as given above.
Note: In Chrome Network, I could my angular service is being called 2 times. First with Request Method: OPTIONS and second time with Request Method: Get, which returns Http 302.
Does anyone know how to resolve this issue.
Thanks in advance.
Because the request is external and because you are serving the application locally you will have CORS issues.
To avoid such issues locally (when using ionic serve), you have to setup a local proxy in the ionic configuration files.
Check your Ionic 2 project directory and locate the file ionic.config.json: it usually is in the root directory of the project (and need to be there, along with package.json and so on).
Open the file, and add this (do not forget to be SURE that the line BEFORE that one ends with a comma (,), since it's a json file):
"proxies": [
{
"path": "/server",
"proxyUrl": "http://phi.dev"
}
]
Now, in the section where are you are performing the HTTP request, replace the http://phi.dev with /server. I will give you an example here.
I do recommend you, however, to be aware that such edit will make your compiled app to NOT work, so you likely want to put a debug flag for testing and compiled environments, like this:
class MyServiceOrComponent {
private debug: boolean = true; // Set this flag to FALSE when you need to actually compile the app for any real device.
private server: string = this.debug ? "/server" : "http://phi.dev";
constructor(private http: HTTP) {
const login = "/api/login"; // don't to it exactly like that, make a static list or something like this to store paths.
let request = this.http.get(this.server + login).then((res) => {
console.log(res);
});
}
}
What happens, explained briefly, is that if you perform the HTTP request as "localhost" it will throw you an exception (because of the CORS policy). Such will happen only when you are running the application in your testing environment (localhost). To avoid such, you provide a proxy, so that the request will be valid.

Call Django API running on a server from Angular running locally

I am learning with Django and Angular.
I have setup a Django API back-end on on http://serverip:8666/athletics/
I have created a small Angular application that I am running from my local machine.
The following code in my Angular app:
$scope.list_athletes = function(){
console.log('hey');
$http
.get('http://serverip:8666/athletics/')
.success(function (result) {
console.log('success');
})
}
generates the error:
XMLHttpRequest cannot load http://serverip:8666/athletics/. No
'Access-Control-Allow-Origin' header is present on the requested
resource. Origin 'http://127.0.0.1:65356' is therefore not allowed
access.
What causes this error? How can I resolve it so that I can access the Django API from my local Angular app?
The problem you're having is related to not having CORS enabled.
As a security policy, JavaScript can't make requests across domains while running in your browser. This is meant to prevent untrusted code from executing without the user's knowledge. The workaround is to enable CORS by white listing domains.
You need to set the Access-Control-Allow-Origin response header in your responses like so:
def my_view(request):
data = json.dumps({'foo':'bar'})
response = HttpResponse(data)
response['Access-Control-Allow-Origin'] = 'http://127.0.0.1:65356'
return response
This will enable CORS for your angular app. You can even add django-cors-headers to your project to have this functionality implemented for you. This can be added to any Django response object, such as django.http.repsonse.HttpResponse. Because you appear to be using a DRF Response object, you may need to use something like
return Response(serializer.data, headers={'Access-Control-Allow-Origin': 'http://127.0.0.1:65356'})
to set your response headers.
You should also check out this site for more information on how to enable CORS in your webapp.
Have you done the settings part in settings.py
INSTALLED_APPS = (
'corsheaders',
)
MIDDLEWARE_CLASSES = (
'corsheaders.middleware.CorsMiddleware',
)
CORS_ORIGIN_WHITELIST = (
'http://127.0.0.1:65356'
)
And also include CORS_ALLOW_CREDENTIALS, CORS_ALLOW_HEADERS settings

GET request throws error after app implemented SSL: Mixed Content: This request has been blocked; the content must be served over HTTPS"

Mixed Content: The page at 'https://www.example.com/dashboard' was
loaded over HTTPS, but requested an insecure XMLHttpRequest endpoint
'http://api.example.com/inventory/10/'. This request has been blocked;
the content must be served over HTTPS.
We have this Angular web app that runs with Flask on the back-end.
Everything was working fine until we implemented SSL. Afterwards, we keep getting this strange error everywhere.
Now, the $http.get request in my dashboard.js is definitely calling "https://api.example.com/inventory/10" in the code below and yet the error is claiming that we are trying to request "http" instead.
$http.get($rootScope.baseUrl+'/inventory/' + item.id)
where rootScope.baseUrl is "https://api.example.com".
It's really weird because some GET requests ARE going through from our web application to our back-end, but some requests are throwing this weird error.
Here's the header that gets an error in our Network tab of the console in chrome.
Request URL:https://api.example.com/inventory/10 Request Headers
Provisional headers are shown Accept:application/json, text/plain, /
Origin:https://www.example.com
Referer:https://www.example.com/dashboard
It was a weird case that came down to removing a forward slash from the end of a URL fixing everything. Somehow, whenever we made a GET request using $http in Angular like baseurl + inventory.id + "/", it would make a http request but as soon as remove that slash, it would make the https request correctly.
Still so confused
I think the root of the problem is in server redirects. I was able to resolve same issue with SECURE_PROXY_SSL_HEADER = ('HTTP_X_FORWARDED_PROTO', 'https') setting for Django (its running behind AWS balancer). Here is documentation.

Resources