Reputation: 509
In my Flask application, I have a simple form of type POST and 4 radio-buttons options with the same name. When I choose an option and press "next" (a submit-type input), a new page loads with different content but a form of the same type.
The issue is, if I refresh the newly loaded page, the form is submitted with the option having the same value as the previously chosen option.
Form:
<form id="myForm" name="myForm" method="post" >
<table align="center" cellpadding="10" border="0" style="background-color: antiquewhite;">
<tr>
<td rowspan="2"><h3>Is this an <i>origin</i> for the <i>claim?</i></h3></td>
<td><input type="radio" name="op" id="op1" value="1" >Yes</td>
<td><input type="radio" name="op" id="op2" value="2" >No</td>
<td rowspan="2"><input type="submit" value=Next></td>
</tr>
<tr>
<td><input type="radio" name="op" id="op3" value="3" >Invalid Input</td>
<td><input type="radio" name="op" id="op4" value="4" >Don't Know</td>
</tr>
</table>
</form>
Snippet of Python code dealing with form:
if request.method == 'POST':
op = request.form.get('op')
if op:
if op in ['1', '2', '3', '4']:
save_annotation(session.get('claim'),session.get('origin'), op, name)
c_url, o_url = get_least_annotated_page(name, session['claim'])
else:
c_url = session['claim']
o_url = session['origin']
else:
print("NOT POST AND LOGGED IN")
c_url, o_url = get_least_annotated_page(name)
.
.
.
.
.
return render_template('index.html',t1=c_url, t2=o_url)
I just want to be able to refresh the page without the form being POSTed.
I already tried using
document.getElementById("myForm").reset();
as well as
<body onload="document.myForm.reset();">
and
autocomplete="off"
Full code available here(annotator.py, app/templates/index.html, and app/templates/base.html):
https://github.com/MohamedMoustafaNUIG/AnnotatorVM.git
EDIT:session is just a global variable that I use to store stuff. name is initialised in the beginning of the python code, and save_annotation() and get_least_annotated_page() are functions.
EDIT2: When a new page is loaded, the buttons are all unchecked. Yet when I refresh, an option is submitted. I only noticed by looking through the command line output.
Upvotes: 1
Views: 1996
Reputation: 509
I found a working solution. It might need more testing before I am sure, but for now it is working fine.
Basically, Ill keep a variable that will be incremented when the user chooses an option. Ill then compare the value stored in session (server-side) with the version sent in the form by the POST request. If they are the same, then this is a refresh, otherwise it is a normal submit.
Code:
Client-side (index.html)::
<form method="post">
<table align="center" cellpadding="10" border="0" style="background-color: antiquewhite;">
<tr>
<td rowspan="2"><h3>Is this an <i>origin</i> for the <i>claim?</i></h3></td>
<td><input type="radio" name="op" id="op1" onchange="incAlpha();" value="1" >Yes</td>
<td><input type="radio" name="op" id="op2" onchange="incAlpha();" value="2" >No</td>
<td rowspan="2"><input type="submit" value=Next></td>
</tr>
<tr>
<td><input type="radio" name="op" id="op3" onchange="incAlpha();" value="3" >Invalid Input</td>
<td><input type="radio" name="op" id="op4" onchange="incAlpha();" value="4" >Don't Know</td>
</tr>
</table>
<input type="hidden" id="alpha" name="alpha" value={{alpha}}>
</form>
<script type="text/javascript">
var globFlag=true; // use so that the incrementation is only triggered once every page load
function incAlpha()
{
if(globFlag)
{
let value= document.getElementById("alpha").value;
document.getElementById("alpha").value = (parseInt(value)+1)%10;
globFlag=false;
}
}
</script>
Python (Flask) Code:
name = session.get('username')
alphaFromSession = session.get('alpha')
if request.method == 'POST':
op = request.form.get('op')
alphaFromClient = request.form.get('alpha')
if op and not (alphaFromSession == alphaFromClient):
if op in ['1', '2', '3', '4']:
save_annotation(session.get('claim'),session.get('origin'), op, name)
session['alpha']=alphaFromClient
c_url, o_url, src_lst, donePg, totalPg, done, total = get_least_annotated_page(name, session.get('claim'))
.
.
.
.
return render_template('index.html',t1=c_url, t2=o_url,alpha=session.get('alpha'))
Upvotes: -1
Reputation: 2050
When you refresh the page the browser will perform the last action, in your case a POST.
The way to avoid this would be to change the return to a redirect instead of render:
if request.method == 'POST':
...
return redirect(url_for('this_view'))
...
Upvotes: 1
Reputation: 1
You can try:
document.getElementById("op1").prop('checked', false)
this will uncheck the radio button. This can be done to each one.
Upvotes: -1