plagiarism detector python flask error method not found - python

I am developing a plagiarism detection tool using flask and python and I am getting the error "Method Not Allowed The method is not allowed for the requested URL.". The project allows a user to upload two files to be compared. Whenever I click on the submit button in the html form then the above error occurs. Can you please suggest some changes?
from io import FileIO
from flask import Flask
from flask import render_template
from flask import request
from flask.helpers import url_for
from werkzeug.utils import redirect, secure_filename
import os
import numpy as np
app=Flask(__name__)
#app.route("/")
def home():
return render_template('upload.html')
#app.route("/upload", methods=["GET", "POST"])
def upload():
if request.method == "POST":
f1 = request.files['file1']
f2 = request.files['file2']
return redirect(url_for('user'))
else:
return render_template('upload.html')
#app.route("/")
def user():
return f"<h1>success</h1>"
if __name__=='__main__':
app.run(debug=True)
my html code snippet from upload.html is:
<form enctype="multipart/form-data" method="post">
<label for="file1">Upload first file here:</label>
<input type="file" id="file1" name="file1"><br><br>
<label for="file2">Upload second file here:</label>
<input type="file" id="file2" name="file2"><br><br>
<input type="submit" value="Submit">
</form>

You're missing an action in your form. In your implementation, it tries to send a POST request to home(), not upload(). That's why you're getting Method not allowed message.
<form action="/upload" enctype="multipart/form-data" method="post">
<label for="file1">Upload first file here:</label>
<input type="file" id="file1" name="file1"><br><br>
<label for="file2">Upload second file here:</label>
<input type="file" id="file2" name="file2"><br><br>
<input type="submit" value="Submit">
</form>

Related

using flask_wtf.csrf without wtf_forms

I have a simple flask web app and I want to use flask_wtf csrf protection but whenever I try to run to submit the form I get an error saying I am missing the CSRF token.
Is it even possible to use csrf without wtf forms?
and if so what am I doing wrong?
my code:
app = Flask(__name__)
csrf = CSRFProtect(app)
#app.route("/reserve", methods=["GET", "POST"])
def reserve():
if request.method == "GET" :
return render_template("reserve.html", **context)
<form id="Reserve" action="/reserve" method="post">
<!-- csrf protection -->
<input type="hidden" name="csrf_token" value="{{ csrf_token() }}"/>
<input type="text" placeholder="Name">
<button type="submit">
Submit
</button>
</form>
Looking your code, you need to init app with csfr, an example below:
from flask_wtf.csrf import CSRFProtect
from flask import Flask,render_template,request,redirect
app = Flask(__name__)
csrf = CSRFProtect(app)
csrf.init_app(app)
app.config['SECRET_KEY'] = 'SUPER SECRET KEY TEST'
#app.route("/reserve", methods=["GET", "POST"])
def reserve():
context = {
'gh':'as'
}
if request.method == "GET" :
return render_template("reserve.html", **context)
else:
user = request.form['ssss']
return 'USER : '+user
#app.route("/")
def index():
return redirect('/reserve')
and html
<form id="Reserve" action="/reserve" method="post">
<!-- csrf protection -->
<input type="hidden" name="csrf_token" value="{{ csrf_token() }}"/>
<input type="text" placeholder="Name" name='ssss'>
<button type="submit">
Submit
</button>
</form>

form action in flask not redirecting to the route

Simply I am just trying to redirect to an url by using the below code in my login.html template:
<form>
<form action="/sessions">
<p>Username:</p>
<p><input type="text" minlength="8" name="username"required /></p>
<p>Password:</p>
<p><input type="text" name="password"/></p>
<input type="submit" value="Submit">
</form>
and
def login():
print("inside login")
return render_template('login.html')
#app.route("/sessions", methods=["GET","POST"])
def sessions():
userid = request.form.get("userid")
password = request.form.get("password")
return request.form.get("userid"), request.form.get("password")
but is stuck on the login() url. Also I tried
<form action="{{ url_for('sessions') }}">
but is not working as well. Not sure what I am missing? Please any hints/ideas would be highly appreciated.
Try this ( i just added one more line, the commented one):
#app.route("/sessions", methods=["GET","POST"])
def sessions():
userid = request.form.get("userid")
password = request.form.get("password")
if request.method == 'POST': #additional line
return request.form.get("userid"), request.form.get("password")
Updated answer reflects new comments
Found couple issues in your code:
HTML form is incorrect, you are using form in form
<form>
<form action="/sessions">
<p>Username:</p>
<p><input type="text" minlength="8" name="username"required /></p>
<p>Password:</p>
<p><input type="text" name="password"/></p>
<input type="submit" value="Submit">
</form>
You should change it to this
<html>
<body>
<h1>This is login page</h1>
<form action="{{ url_for('login') }}" method="POST">
<p>Username:</p>
<p><input type="text" minlength="8" name="username"required /></p>
<p>Password:</p>
<p><input type="text" name="password"/></p>
<input type="submit" value="Submit">
</form>
</body>
</html>
Notice changes, first there is only 1 form tag, then I use jinja2 engine to call the login in form.action, 2nd this login page handles serving login HTML when there is a GET request (initially opening this page) and for accepting form POST request with credentials.
Then I changed the routes to this:
from flask import Flask, render_template, request, redirect, url_for
app = Flask(__name__)
#app.route('/login', methods=['GET', 'POST'])
def login():
if request.method == 'POST':
user_name = request.form['username']
password = request.form['password']
print(user_name, password) # do something here?
return redirect(url_for('session'))
return render_template('login.html')
#app.route('/session')
def session():
return render_template('session.html')
Notice that now login accepts both methods, GET and POST, as mentioned before, GET is for serving HTML content and POST is for submitting form data. In the login endpoint I have a condition that checks, if it's a POST method request, then I extract credential details from request.form and after doing something (e.g. in that print() statementIreturn redirect(url_for('session'))`.
This is how you manage redirects from one page to another by clicking submit on one of a pages.
original answer that was incorrect
In Flask to redirect, you could you something like this:
from flask import url_for, redirect
#app.route('/sessions', methods['GET', 'POST']
def sessions():
# some code
return redirect(url_for('some.endpoint'))
This will redirect you to a specific endpoint that you will provide. In the docs there is more info about it.

how to stop a page from relaoding after the button submit is clicked

when i click on my submit button,It reload the index.html.I want it to be in the same /registers page.How i can do it?
i tried redirect(url_for("registers")) but its does not work
from flask import Flask,render_template,request
import csv
app= Flask(__name__)
#app.route("/")
def index():
try:
file = open("registered.csv","r")
reader=csv.reader(file)
students=list(reader)
return render_template("index.html",students=students)
except:
return("Fails")
#app.route("/register",methods=["post"])
def register():
if not request.form.get("details"):
return("fails")
else:
file = open("registered.csv","a")
writer = csv.writer(file)
writer.writerow((request.form.get("details")))
file.close()
file = open("registered.csv","r")
reader=csv.reader(file)
students=list(reader)
return render_template("index.html",students=students)
This must be defined in your page template, using the action attribute of <form>.
Example:
<form action="/action_page.php" method="get">
First name: <input type="text" name="fname"><br>
Last name: <input type="text" name="lname"><br>
<input type="submit" value="Submit">
</form>
Of course, the destination url can be defined using a variable when rendering the page.

Flask- method not allowed despite using POST [duplicate]

This question already has answers here:
Flask - POST Error 405 Method Not Allowed
(3 answers)
Closed 3 years ago.
I am attempting to create a basic login page on a raspberry pi, but when I try to login to the page I keep getting a 405 error. I have researched the issue but it seems to only appear if you aren't using the correct methods, but since it's a login screen POST and GET should be more than sufficient.
Python
from flask import Flask
from flask import Flask, flash, redirect, render_template, request, session, abort
import os
app = Flask(__name__)
#app.route('/')
def home():
if not session.get('logged_in'):
return render_template('login.html')
else:
return "Hello Boss!"
#app.route('/login', methods=['POST', 'GET'])
def do_admin_login():
if request.form['psw'] == 'password' and request.form['id'] == 'admin':
print ("Hey ya!")
else:
print('wrong password!')
return home()
if __name__ == "__main__":
app.secret_key = os.urandom(12)
app.run(debug=True,host='0.0.0.0', port=80)
HTML
<!DOCTYPE html>
<html>
<body>
<h1>Please login</h1
<form method="POST">
<input name="id" type="text" placeholder="Enter UserID">
<br>
<input name="psw" type="password" placeholder="Enter Password">
<input type="submit">
</form>
</body>
</html>
I have been redirected to a different question which resolves it through changing the action part of the however mine does not have action so this should not be the same issue. I have attempted adding an action element to it but that has not changed anything
The problem is that you need to specify the action attribute in HTML:
<form method="POST" action="{{url_for('do_admin_login')}}">
<input name="id" type="text" placeholder="Enter UserID">
<br>
<input name="psw" type="password" placeholder="Enter Password">
<input type="submit">
</form>
As you may notice that I used url_for function to generate a URL to the given endpoint with the method provided ( do_admin_login() in this case ). So it is worth to mention that you need to change your statement return home() to return url_for("home").

Python Flask : url_for to pass the variable to function from form template

I tried this approach to pass the form input variable to function via url_for method. But its not working. can anyone check and let me know whats wrong in this code.
Function:
#app.route('/report_data/<year>/<week>', methods = ['POST'])
def report_data(year,week):
print year
print woy
HTML Code :
<html>
<body>
<form action="{{ url_for('report_data', year=n_year, week=n_woy) }}" method="post">
<h3> Enter the details </h3>
Year :
<input type="text" name="n_year"> <br>
<br>
Week :
<input type="text" name="n_woy"> <br>
<br>
<input type="submit" value="Submit"> <br>
</form>
</body>
</html>
Issue:
Getting "None" for both variable.
Firstly, How do you provide year, week values before submitting them in your HTML code ?
Did you render the HTML template in your function? If not, how does your flask function knows that you were seeking from that specific form?
If this is your Flask app code -
from flask import Flask, render_template, request
app = Flask(__name__)
#app.route('/report_data', methods = ['POST', 'GET'])
def report_data():
if request.method == 'POST':
result = request.form
query_year = result['n_year'].encode('ascii', 'ignore')
query_week = result['n_woy'].encode('ascii', 'ignore')
print(query_year, query_week)
return render_template('so_test.html')
if __name__ == '__main__':
app.run(debug=True)
And opened the URL -
http://127.0.0.1:5000/report_data
And I get this picture.
Once I post the data, I can see this data in my Flask app console.
('2018','08')

Categories