I have an app in Heroku running with Django.
Now I'm starting to develop a Phonegap app that I want to make work with my Heroku app.
I can't make it work because of CORS (Cross-origin resource sharing) protection. So I need to exclude some urls (not all app) to make my Phonegap app work.
I've tried installing django-cors-headers, but it doesn't seem to work.
To test it, I'm making a call to obtain a csrf_token.
I added this to my setting.py (and of course followed the guide, setting all to default):
CORS_URLS_REGEX = r'^register/.*$'
CORS_URLS_REGEX = r'^login/.*$'
CORS_URLS_REGEX = r'^getcsrf/.*$'
And this is the Ajax call I try to make:
get: function() {
$.getJSON("http://domain.herokuapp.com/getcsrf/",
{
tags: "jquery,javascript",
tagmode: "any",
format: "json"
},
function(data) {
$.each(data.items, function(item){
console.log(item);
});
});
}
But I get this marked in red as an error and an empty response field:
GET http://domain.herokuapp.com/getcsrf/?tags=jquery%2Cjavascript&tagmode=any&format=json 200 OK 206ms
There's no cross origin restrictions with phonegap, it's using a webview, not a web browser.
The only thing you have to do with phonegap/cordova is to be sure your server is whitelisted in config.xml.
In cordova 3.3/3.4, the default setting is <access origin="*" /> which should allow access to any url.
Related
I have a public cloud VM which has public IP say 160.159.158.157 (this has a domain registered against it).
I have a Django application (backend) which is CORS-enabled and serves data through port 8080.
I have a React app running on the same VIM on a different port (3000), which is accessing the Django app and is supposed to produce a report.
The problem is that, when I use http://<domain-name>:8080/api/ or http://<public-ip>:8080/api/, my application is working fine,
but when I try to fetch data from localhost like http://localhost:8080/api/ or http://127.0.0.1:8080/api/, the React app fails to fetch data with the following error:
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource at http://127.0.0.1:8080/api/. (Reason: CORS request did not succeed). Status code: (null).
Here's what I've tried:
axios.get(baseURL, { headers: {
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Methods':'GET,PUT,POST,DELETE,PATCH,OPTIONS',
}
but it didn't work. What should I do?
Looks like you've gotten confused where those headers need to be. You're setting them on the request to the backend, but they need to be set on the response from the backend. After all, it wouldn't be very good security if someone making a request could simply say "yeah, I'm ok, you should trust me".
The problem is going to be somewhere in your backend Django app, so double check the CORS config over there.
Hey guys I am doing a project that uses Python as a backend and React as a frontend. Everything works fine. After deploying to heroku I changed all my axios request URL to my domain name. But I realize if I change my domain name I have to change the axios URL in my react app everytime. I have used redux to do perform axios request for CRUDL and all types of authentication. I know this sounds stupid but is there a way to configure all the axios request to particular domain name by only giving path name every time it makes request? Thanks
setup axios defaults something like this:
axios.defaults.baseURL =
process.env.NODE_ENV === "production"
? process.env.REACT_APP_PROD_URL
: process.env.REACT_APP_DEV_URL;
then in your .env file
REACT_APP_PROD_URL="https://api.example.com"
REACT_APP_DEV_URL="http://localhost:8000"
i am new to backend dev. I try to developp a flask restful api. I followed the documentation and made the suggested minimal api, that is just returning a jsonified dict. With postman, curl and in the browser, no problem, the api is running and responds to my requests.
From my react native app however, i always get a Netwrok Error.
I tried lots of things:
- multiple IP addresses for the flask serveur
- differents ways to use axios
- different os : win10, ubuntu
- different endpoints : /, /api, /test
- different ways of writing the api (flask-restful class, flask app functions ...)
- manips from web documentations : dev mode of my device, chrome dev tools (port forwarding)
- i asked a react native developper to check my client-side code, nothing wrong according to him,
precisions :
- python code runs under a conda virtual env
- appli runs under node js and expo
- container folders of my app and my api are at the same level
- the flask server does not respond 404 or whatever, it does not respond at all, the error returned in react native is a network error
- depending on url, the network errors occurs immediately or after a 2 minutes delay
- flask shows requests and status when called by postman, curl, chrome, but does not react when i press my buttons from the react native app
Here is (one of) my python code:
from flask import (Flask, jsonify)
# from flask_restful import Resource, Api
from flask_cors import CORS, cross_origin
app = Flask(__name__)
CORS(app)
#app.route("/api", methods=["GET"])
def get():
return jsonify(hello='bouh !')
if __name__ == '__main__':
app.run(host="0.0.0.0", port=5000, debug=True)
and here is the clientside code:
import React, {Component} from 'react';
import { View, Button } from 'react-native';
import axios from 'axios';
import { sharedStyles } from '../../SHARED/_shared';
var url = "http://192.168.1.16:5000/api";
export default class PrevCommune extends Component {
constructor(props){
super(props);
this.navigation=this.props.navigation;
};
getAxios=()=>{
axios.get(`${url}`).then((response)=>{
console.log("succes axios :",response);
}).catch((error)=>{
console.log("fail axios :", error);
});
};
getFetch=()=>{
fetch(url).then((response)=>{
console.log("succes fetch :",response)
}).catch((error)=>{
console.log("fail fetch :",error)
})
}
render(){
return (
<View style={sharedStyles.mainContainer}>
<Button onPress={()=>this.getAxios()} title={"get axios"}></Button>
<Button onPress={()=>this.getFetch()} title={"get fetch"}></Button>
</View>
);
};
};
And the lines returned by requests:
fail axios : [Error: Network Error]
fail fetch : [TypeError: Network request failed]
I saw lots of tutos, videos, articles on flask api but i didn't find where i am wrong. Please tell me if you have any ideas ! I think both client and server codes are ok, the problem seems to be that my requests are blocked by something.
Solved : the probleme was my firewall ... thank you ricardo for the CORS doc =)
What worked for me was to change the IP address of localhost to my network IP in the api call in react native and then starting the flask application using the below command.
flask run --host=0.0.0.0
I have an app Vue + Django. I try to send some data from vue to database using axios post method. Unfortunately console shows error:
GET http://localhost:8080/api/get_data/ 404 (Not Found)
And the same happend in python console:
Not Found: /get_data/
I have function get_data defined in my views and i added a path to urls:
path('get_data/', views.get_data)
In frontend it looks like this:
addNewData() {
axios.post("/api/get_data/", this.componentData.data).then(response => {
console.log("ok");
});
}
Did I missed something?
axios.post("/api/get_data/" - this URL is relative to "current". That's why it is trying ot access http://localhost:8080/... where 8080 is the port of VUE app. Whereas Django app is running by default on 8000.
You should use absolute URLs to access one app from another: to access Django app API from Vue app.
Use different config/env.var in your VUE app to refer to backend API in debug (localhost) and prod (domain name + http/https) modes, like:
axios.post(conf.BACKEND_URL + "/api/get_data/")
in your case, in debug mode it should be (expanded):
axios.post("http://localhost:8000/api/get_data/")
if you don't used webpack proxyTable deal with '/api' ,you should add the backend address
I have a node web client called bidsell, and a small Python Tornado REST API called quote. Bidsell when triggered makes regular http get calls to quote. Quote duely returns random price information as json. Works locally - want to share it online, but how? Heroku looks promising. Have tried already to deploy both bidsell and quote in the same project on heroku, each running within their own heroku web dyno or deployment container. From the logs "heroku log" both are installed correctly but only one appears to be running. So I can access the front page url of bidsell, for example, but when bidsell is triggered to go fetch quote info the quote service is not found :-( Should I be using another deployment pattern?
ok so as jr0cket suggested I created 2 heroku projects - one for the bidsell node project and one for the quote service.
In addition to the bidsell node project source files I had a procfile containing the following:
web: npm start
and a scripts section in package.json informing heroku how to start the app:
"scripts": {
"start": "gulp serve"
}
In addition to the quoteService source python file I had a procfile containing the following:
web: python quoteService.py
and a requirements.txt file containing:
tornado==3.1.1
pyrestful==0.4.1
Had the following proxy.js as middleware in the bidsell app:
'use strict';
var proxyMiddleware = require('http-proxy-middleware');
var options = {
target: 'http://quoteservce.herokuapp.com:80',
changeOrigin: true
};
var proxy = proxyMiddleware('/quote', options);
module.exports = function(){
return [proxy];
}
being called from server.js:
'use strict';
..
var middleware = require('./proxy');
module.exports = function(options) {
function browserSyncInit(baseDir, browser) {
browser = browser === undefined ? 'default' : browser;
..
var server = {
baseDir: baseDir,
routes: routes
};
server.middleware = middleware();
browserSync.instance = browserSync.init({
port: (process.env.PORT || 5000),
startPath: '/',
server: server,
browser: browser
});
}
..
gulp.task('serve', ['watch'], function () {
browserSyncInit([options.tmp + '/serve', options.src]);
});
..
};
to allow communication between bidsell and quoteService. For further background info take a look here
The running app you can find here.
May take a little while for the idle free-tier heroku dynos to fire up ;-)
Bidsell project on git.
QuoteService project on git.
As your project is two seperate technology stacks, the easiest approach is to deploy these as two separate Heroku apps. This gives you simple way to create the specific environment (languages, runtimes, libraries) needed for each app / service.
You could create an Heroku configuration variable QUOTE_REST_API for the node web client that points to the external web address. For example, using the heroku toolbelt
heroku config:set QUOTE_REST_API=https://quote-api.herokuapp.com/
Using the QUOTE_REST_API configuration variable in your node client would give a simple way to change the address of the quote without having to change your code.
If you are running two separate projects in one Heroku app, you need to ensure that you have two web: entries for the Procfile to start your separate processes. Only processes marked as web will listen to web traffic.
You may not be able to run two different web processes if you use the free tier of heroku.