Python Requests package hits url twice - python

I am trying to create a synonym list for words by hitting a synonyms api. I am using Flask and the requests package.
I am calling this function only once after grabbing information from a webform via a flask route.
Code:
import requests
from flask import Flask, request, render_template, flash
import environment
app = Flask(__name__)
#app.route("/", methods=["GET", "POST"])
def index():
if request.method == "POST":
keywords = request.form["key1"]
synonyms = syn_look(keywords)
return render_template("index.html", syns=synonyms)
return render_template("index.html")
def syn_look(word):
URL = "http://words.bighugelabs.com/api/2/%s/%s/json"
request_url = URL %(environment.thesaurus_api_key, word)
r = requests.get(request_url)
print r.status_code
if __name__ == "__main__":
app.debug = False
app.run()
The status prints twice
output:
* Restarting with reloader
* Detected change in 'server.py', reloading
* Restarting with reloader
127.0.0.1 - - [10/Jan/2014 17:22:03] "GET / HTTP/1.1" 200 -
200
404

Are you certain you're formatting request_url correctly?
You can see in the GET request, a 404 is printed on the last line. This is the HTTP 404 Error, file not found. I'm betting this is why you see the 'reloading' messages in the console output.

Related

redirect a POST to GET request

I'm trying to understand what is the best way a POST request can be redirected to a GET request.
for example -
POST /redirect HTTP/1.1
Host: www.example1.com
url=www.example2.com
and i've created the following flask to help me with that :
from flask import Flask,request, redirect
app = Flask(__name__)
#app.route('/redirect',methods=['POST'])
def redire():
url = request.form['url']
return redirect('https://www.example2.com', code=307)
if __name__ == '__main__':
app.run(host='0.0.0.0', port=8888)
the "issue" in my case, is that the request that is being sent to
https://www.example2.com
is also a POST request which is not what i wanted.
Consider that I don't "care" about the body that needs to be sent to the
https://www.example2.com
endpoint, what is the best way to do so without any user intervention (meaning that I'm aiming for an auto redirect).
Note: I've tried to do it via PHP but I can't seem to figure it out.
Apologies if something is not clear.
In order to redirect a POST request to a GET request, you need to use code=303 because it requires the client to use the GET method to retrieve the requested resource.
#app.route('/redirect',methods=['POST'])
def redire():
url = request.form['url']
return redirect('https://www.example2.com', code=303)
the server
from flask import Flask, redirect
app = Flask(__name__)
#app.route('/redirect', methods=['POST'])
def redire():
return redirect('http://127.0.0.1:8888/get')
#app.route('/get', methods=['GET'])
def iam_get():
return {"code": "ok"}
if __name__ == '__main__':
app.run(host='0.0.0.0', port=8888)
the client
import requests
data = requests.get("http://127.0.0.1:8888/get")
print(data.text)
data = requests.post("http://127.0.0.1:8888/redirect")
print(data.text)
the result as follows
{"code":"ok"}
{"code":"ok"}

IIS returning 500 Internal Server Error for POST but working for GET- Flask

I am facing an issue with my flask program.
I hosted a flask application on IIS running on Win 11. But from Postman I am Getting Get response but 500 error when Methos = POST.
But there is no error when running the same code from VS Code.
My Flask code:
import decodedata
import Call_printer
from flask import Flask, request, render_template,jsonify
app = Flask(__name__)
#app.route('/print',methods = ['GET','POST'])
def printer():
if request.method == 'POST':
req_data = request.json
print(req_data)
data = req_data['data']
printername= req_data['printername']
xml = decodedata.decode_xml(data)
msg = Call_printer.sendprintjob(printername,xml)
status={"Status":msg}
return jsonify(status)
if request.method == 'GET':
return "Hello World."
if __name__ == '__main__':
app.debug = True
app.run()
Below is an error when running from IIS.
Error in IIS
Below is the correct POST Response from VS CODE
Success in VS Code
But I am receiving responses in GET method from IIS. Only for POST, I am receiving 500 error?
Can it be because I am calling other py files for POST?
Any idea how can I fix it?
Regards,
Mayank Pande

flask endpoint which is defined returns 404

from flask import Flask, jsonify, request
app = Flask(__name__)
app.users = {}
app.id_count = 1
#app.route("/ping", methods = ['GET'])
def ping():
return "pong"
#app.route("/sign-up",methods = ['POST'])
def sign_up():
new_user = request.json
new_user["id"] = app.id_count
app.users[app.id_count]= new_user
app.id_count = app.id_count +1
return jsonify(new_user)
if __name__ =='__main__':
app.run()
I tried to send a HTTP request to endpoint /sign-up which is defined as above,
127.0.0.1 - - [22/Nov/2021 22:02:02] "POST /sign-up HTTP/1.1" 404 -
It seems like a really simple problem and I don't see it.
I was running these on WSL2 ubuntu. (both server and client)
and I eventually tried running this on my Windows Pycharm which is not a virtual machine, and it worked fine.
I wonder why /ping works fine tho, will be finishing this course on ordinary windows from now on for sure

how to use flask driver in python splinter

all my code is just:
from splinter import Browser
from flask import Flask, request
from splinter.driver.flaskclient import FlaskClient
app = Flask(__name__)
browser = Browser('flask', app=app)
browser.visit('https://www.google.com')
print(browser.html)
which print the 404 html:
404 Not Found
Not Found
The requested URL was not found on the server. If you entered the URL manually please check your spelling and try again.
there is anything I should do?
You are getting a 404 error because your Flask app has no routes.
I believe the purpose of the Splinter Flask client is to test your Flask app, not to test/request other domains. Visiting another domain with the Splinter Flask client will simply request the URL from your domain. You have not specified any routes for your Flask app, so Flask is responding with a 404 error.
Here's an example that shows how the Splinter Flask client is working:
# define simple flask app
from flask import Flask
app = Flask(__name__)
#app.route('/')
def hello_world():
return 'Hello, World!'
#app.route('/<name>')
def hello_world(name):
return 'Hello, {name}!'.format(name=name)
# initiate splinter flask client
from splinter import Browser
browser = Browser('flask', app=app)
# simple flask app assertions
browser.visit('http://127.0.0.1:5000')
assert browser.html == 'Hello, World!'
browser.visit('http://127.0.0.1:5000/haofly')
assert browser.html == 'Hello, haofly!'
# Notice that requesting other domains act as if it's your domain
# Here it is requesting the previously defined flask routes
browser.visit('http://www.google.com')
assert browser.html == 'Hello, World!'
browser.visit('http://www.google.com/haofly')
assert browser.html == 'Hello, haofly!'
Here's another test that demonstrates what's really going on:
from flask import Flask
app = Flask(__name__)
#app.errorhandler(404)
def page_not_found(e):
return 'Flask 404 error!', 404
from splinter import Browser
browser = Browser('flask', app=app)
browser.visit('http://www.google.com/haofly')
assert browser.html == 'Flask 404 error!'

Add response headers to flask web app

I have a flask web app which uses render_template as follows.I need to add a Content-Security-Policy as additional http response headerin the response. I tried following ways but both fail and give me 500.
1.
from flask import \
Flask, \
render_template
app = Flask(__name__,template_folder='tmpl')
#app.route('/')
def index():
resp =make_response(render_template('index.html'))
resp.headers['Content-Security-Policy']='default-src \'self\''
return resp
if __name__ == '__main__':
app.run(host='0.0.0.0', port=3001)
2.
#app.route('/')
def index():
resp =render_template('index.html')
resp.headers.add('Content-Security-Policy','default-src \'self\'')
return resp
if __name__ == '__main__':
app.run(host='0.0.0.0', port=3001)
What can be wrong here?
On the terminal i see following when I access the web app as localhost:3001
127.0.0.1 - - [06/Apr/2015 01:45:01] "GET / HTTP/1.1" 500 -
render_template returns a string, not a response. A string returned from a view is automatically wrapped in a response by Flask, which is why you may be confused. Construct the response with the rendered template.
from flask import make_response
r = make_response(render_template('index.html'))
r.headers.set('Content-Security-Policy', "default-src 'self'")
return r
The prettiest way to handle this, assuming that you want to same headers attached to all of your responses is with flasks builtin decorator:
#app.after_request
So in this case just add this function to your routes module:
#app.after_request
def add_security_headers(resp):
resp.headers['Content-Security-Policy']='default-src \'self\''
return resp
With this in place your functions just return the render_template(...) value as before and flask automatically wraps it in a response which is passed to the after_request function before being returned to the client.

Categories

Resources