How to convert POST request to GET request in flask? - python

I created a web application in flask that has a form and whatever text the user enters appears on the bottom along with all the previously entered messages.
I was trying to load test it using JMeter, but I'm not able to send POST request using multiple threads in JMeter so I wanted to convert the post request to GET request so that I am able to perform load tests on my application.
Currently my route looks something like this
#app.route('/blog', methods=['GET', 'POST'])
#app.route('/', methods=['GET', 'POST'])
def blog():
print
form = PostForm()
if form.validate_on_submit():
post = Post(body=form.post.data)
db.session.add(post)
db.session.commit()
return redirect(url_for('blog'))
posts = Post.query.all()
return render_template('index.html', title='Blogger', form=form,
posts=posts)
What can I do to send the parameters through the URL.
I am very new to web development and I followed the mega tutorial in flask. Is there a workaround this?

add #app.route("/<string:param>",methods['GET']) and give it default values def blog(param = "") and use it for your get method
#app.route("/<string:param>",methods['GET'])
#app.route("/blog/<string:param>",methods['GET'])
#app.route('/blog', methods=['GET', 'POST'])
#app.route('/', methods=['GET', 'POST'])
def blog(param = ""):
print
if request.method == "POST":
##your post code here
elif request.method == "GET":
## new code using 'param' here

Related

How do i send data to a flask app and then have the flask app display it [duplicate]

This question already has answers here:
Sending data from HTML form to a Python script in Flask
(2 answers)
Closed 10 months ago.
I want to send some POST data to a flask webpage then have it display that data but when I try to send the data {"hi": "hi"} it gives me these errors:
code 400, message Bad request syntax ('hi=hi')
"None / HTTP/0.9" HTTPStatus.BAD_REQUEST -
my code is this:
from flask import Flask, request
app = Flask("__name__")
#app.route("/", methods=['GET', 'POST'])
def hi():
return "hi"
if request.method == "POST":
data = request.values
return f"<p>{data}</p>"
the flask app:
and the post data sending program:
import requests
requests.post('http://127.0.0.1:5000', data={ "req": "hi" })
am I just not understanding POST requests right or am I doing something really wrong?
please see this answer regarding how to access the request's data.
the requests.post you are using as http client is sending the data as form-encoded, so we could use Flasks' request.form to access the data. Also your function needs some restructuring, else it will always return "hi", we can make it:
from flask import Flask, request
app = Flask("__name__")
#app.route("/", methods=['GET', 'POST'])
def hi():
if request.method == "GET":
return "hi"
if request.method == "POST":
# data = request.values
# data will be = req if your POST request has req field, else will be = field: req was not provided
data = request.form.get("req", "field: req was not provided")
return f"<p>{data}</p>"
if you dont know the fields the POST request will contain, you can use this loop to get the fields and their values:
#app.route("/", methods=['GET', 'POST'])
def hi():
if request.method == "GET":
return "hi"
if request.method == "POST":
# data = request.values
for field in request.form:
print(field, request.form.get(field))
return "hi"

Flask-wtforms Redirect on Form Submission and Pass Variables

I am struggling to figure out why I am unable to pass variables to my redirected url. I have attempted the suggestions in the following questions, but for some reason they are not working.
redirect while passing arguments
How can I pass arguments into redirect(url_for()) of Flask?
The only thing I can think of is that it is because I am using flask-wtforms to validate the form before the redirect. I haven't seen much in way of answers/suggestions for this scenario. So here I am.
#app.route('/quiz/', methods=['GET', 'POST'])
def quiz():
form = Quiz()
if form.validate_on_submit():
q1_answer = 'North'
return redirect(url_for('result', q1_answer=q1_answer))
return render_template('quiz.html', form=form)
#app.route('/result/', methods=['GET', 'POST'])
def result():
q1_correct_answer = request.args.get('q1_answer')
return render_template('result.html', q1_correct_answer=q1_correct_answer)
The redirect works the way it should. The 'result' url and its corresponding template are rendered. I just can't get the variable (q1_answer) to pass. My template always returns a value of None. Any help would be greatly appreciated.
I think you use it
#app.route('/quiz/', methods=['GET', 'POST'])
def quiz():
form = Quiz()
if request.method == "POST" and form.validate_on_submit():
q1_answer = 'North'
return redirect(url_for('result', q1_answer=q1_answer))
return render_template('quiz.html', form=form)
#app.route('/result/', methods=['GET', 'POST'])
def result(q1_answer):
return render_template('result.html', q1_correct_answer=q1_answer)

render_template in Python-Flask is not working

I am actually creating an app with Flask and I am encountering issues regarding my routing.
My situation is simple: The user enters a token to authenticate himself. Once he clicks on authenticate, an angular HTTP request uses POST to send his token to a Python server. There, if he is granted access, the home page is displayed using render_template; otherwise the login keeps still.
However, when the user authenticates himself, I see on my command line that the POST was successful, the authentication was a success but the page just stuck on login and does not redirect to home page as if the second render_template does not work. Please Help!
#app.route('/')
def index():
if not session.get('logged_in'):
return render_template('auth.html') # this is ok.
else:
return render_template('index.html') # this does not work
#app.route('/login', methods=['POST','GET'])
def login():
tok = request.form['token']
if (check_token(tok) == "pass"): # check_token is a function I've implemented
# to check if token is ok=pass, ko=fail
session['logged_in'] = True
else:
flash("wrong token")
return index()
Your login handler shouldn't call index directly. It should return a redirect to the index.
return redirect('/')
or better:
return redirect(url_for('index'))
I was thinking of the following.
#app.route('/')
def index():
if not session.get('logged_in'):
return return redirect(url_for('login'))
else:
return render_template('index.html')
#app.route('/login', methods=['POST','GET'])
def login():
if request.method = "POST":
tok = request.form['token']
if (check_token(tok) == "pass"):
session['logged_in'] = True
return redirect(url_for('index'))
else:
flash("wrong token")
return render_template("login.html")
I have used Angular JS in my app to send requests to my flask server and i realised that my client side angular JS had difficulties in rendering page as it was just expecting a response.
I first tried to do.. document.write('response.data') and it did display my home page but my scripts attached on my html page stopped working.
Second try, I tried to reload the page after receiving the response in my client and it works well. I don't know if it's the best way to do but it does work.

Flask redirects to wrong view when redirecting to index

I keep running into this strange issue that I can't seem to figure out a solution for. I cannot copy and show all of my code in it's entirety here, but I will try to outline the general structure of my flask app to present my issue.
(Let's ignore all of the content in the /static folder and my helper modules)
I have 3 main views, let's call them viewA, viewB, and index:
viewA.html
viewB.html
index.html
viewA and viewB both display two forms, but with different content (i.e. viewA displays form1 & form2, and viewB also displays form1 & form2).
A simplified version of my script code is as follows:
#imports
from flask import Flask, render_template, session, redirect, url_for, request
from flask_wtf import FlaskForm
#etc. etc.
app = Flask(__name__)
app.config['SECRET_KEY'] = 'blah blah blah'
manager = Manager(app)
bootstrap = Bootstrap(app)
moment = Moment(app)
class FormOne(FlaskForm):
sample_field = StringField('Sample Field:')
class FormTwo(FlaskForm):
other_field = StringField('Other Field:', validators=[Required()])
submit = SubmitField('Submit')
class UploadToA(FlaskForm):
content= StringField('Content to send to view A:', validators=[Required()])
submit = SubmitField('Submit')
class UploadToB(FlaskForm):
content= StringField('Content to send to view A:', validators=[Required()])
submit = SubmitField('Submit')
#app.route('/ViewA', methods=['GET', 'POST'])
def view_a():
"""
A lot of data manipulation
"""
form1 = FormOne()
form2 = FormTwo()
if request.method == 'GET':
"""
populate forms with content
"""
if request.method == 'POST':
if form2.validate_on_submit();
"""
clear session variables
"""
return redirect(url_for('index'), code=302)
return render_template('viewA.html', form1=form1, form2=form2)
#app.route('/ViewB', methods=['GET', 'POST'])
def view_b():
"""
A lot of data manipulation
"""
form1 = FormOne()
form2 = FormTwo()
if request.method == 'GET':
"""
populate forms with content
"""
if request.method == 'POST':
if form2.validate_on_submit();
"""
clear session variables
"""
return redirect(url_for('index'), code=302)
return render_template('viewB.html', form1=form1, form2=form2)
#app.route('/', methods=['GET', 'POST'])
def index():
"""
Some data manipulation
"""
formA = UploadToA()
formB = UploadToB()
if formA.validate_on_submit()':
"""
pull content from form A
create some session variables
"""
return redirect(url_for('view_a'))
if formB.validate_on_submit()':
"""
pull content from form B
create some session variables
"""
return redirect(url_for('view_b'))
return render_template('index.html', formA=formA, formB=formB)
if __name__ == '__main__':
manager.run()
Now the issue at hand I am having here is that for some strange reason when I'm in 'viewA.html' and I submit my form, I SHOULD be redirected back to 'index.html' but for some strange reason it redirects me to 'viewB.html'. Furthermore, the opposite also holds true: when i'm in 'viewB.html' and I submit my form, I SHOULD also be redirected back to 'index.html' but it redirects me to 'viewA.html'. Yet, if I am in either viewA or viewB, I have no issues of going back to the index view if I manually enter the url into my browser.
Any ideas as to why I might be running into this issue?
Thanks in advance :)
I have finally figured out the source of my problem. It turns out that in my 'viewA.html' template file, I had the following in my < form > tag:
<form class="form form-horizontal" method="post" role="form" action="{{url_for('index')}}">
And the problem all lies in that last part:
action="{{url_for('index')}}"
As a result, everytime I would submit form2 in viewA.html it would create a post request for my index page rather than a post request for the viewA.html page (which caused a redirect to the wrong view). Thus, by simply removing the action attribute (action="{{url_for('index')}}"), I was able to solve my problem!
Since the full code isn't here, I can't confirm this for sure, but what I think is happening is this:
You open form A
You submit form A
It sends a redirect to /index
It sends a redirect to /FormB
if formB.validate_on_submit():
return redirect(url_for('view_b'))
This is probably sending a redirect to View B. Try changing that last line to something like return something_else and seeing if it sends that after submitting form A.

Clear valid form after it is submitted

I want to reset the form after it validates. Currently the form will still show the previous data after it is submitted and valid. Basically, I want the form to go back to the original state with all fields clean. What is the correct to do this?
#mod.route('/', methods=['GET', 'POST'])
def home():
form = NewRegistration()
if form.validate_on_submit():
#save in db
flash(gettext(u'Thanks for the registration.'))
return render_template("users/registration.html", form=form)
The issue is that you're always rendering the form with whatever data was passed in, even if that data validated and was handled. In addition, the browser stores the state of the last request, so if you refresh the page at this point the browser will re-submit the form.
After handling a successful form request, redirect to the page to get a fresh state.
#app.route('/register', methods=['GET', 'POST'])
def register():
form = RegistrationForm()
if form.validate_on_submit():
# do stuff with valid form
# then redirect to "end" the form
return redirect(url_for('register'))
# initial get or form didn't validate
return render_template('register.html', form=form)
davidism answer is correct.
But once I had to reload a form with only a few fields that had to be resetted.
So, I did this, maybe it's not the cleanest way but it worked for me:
form = MyForm()
if form.validate_on_submit():
# save all my data...
myvar1 = form.field1.data
myvar2 = form.field2.data
# etc...
# at first GET and at every reload, this is what gets executed:
form.field1.data = "" # this is the field that must be empty at reload
form.field2.data = someobject # this is a field that must be filled with some value that I know
return render_template('mypage.html', form=form)
You can clear a form by passing formdata=None
#mod.route('/', methods=['GET', 'POST'])
def home():
form = NewRegistration()
if form.validate_on_submit():
#save in db
######### Recreate form with no data #######
form = NewRegistration(formdata=None)
flash(gettext(u'Thanks for the registration.'))
return render_template("users/registration.html", form=form)
you can also return new form object using render_template if form does not validates you can also pass message
#mod.route('/', methods=['GET', 'POST'])
def home():
form = NewRegistration()
if form.validate_on_submit():
#save in db
return render_template("user/registration.html", form = NewRegistration())
return render_template("users/registration.html", form=form)

Categories

Resources