Home > Back-end >  how to use multiple request method in Flask
how to use multiple request method in Flask

Time:12-09

I have a textarea and a file upload functions. Now when I want to use the file upload, the method.request is referring to textarea and gives an error, how to handle this problem.

@app.route('/',methods = ['GET','POST'])
def upload_route_summary():
    if request.method == 'POST':
        if request.files['file'] is True:
           # Create variable for uploaded file
            file = request.files['file']
            file.save(os.path.join("uploaded", file.filename))
            return render_template('home.html', message='uploaded successfully')
    return render_template('home.html', message='upload')

and the second function is for the textarea to accept input and display in the table.

@app.route('/', methods=['GET', 'POST'])
def root():
    if request.method == 'GET':
        return render_template('home.html')
    elif request.method == 'POST':
        results = []

        user_csv = request.form.get('user_csv').split('\n')
        reader = csv.DictReader(user_csv)

        for row in reader:
            results.append(dict(row))

        fieldnames = [key for key in results[0].keys()]

        return render_template('home.html', results=results, fieldnames=fieldnames, len=len)

Here is the home.html file:

<div >
<div  >
<form method="post" enctype=multipart/form-data>
  <textarea  rows="5" name="user_csv"> 
 </textarea>
  <button >Render CSV</button>
  <input  type="file" name='file'/>
  <input  type="submit">
 </form>
 <p>
 {{message}}
 </p>
 <div >
  {% if request.method == 'POST'%}
    <table id="proxies"  
    style="width: 100%">
      <thead>
        <tr>
          {% for header in results[0].keys() %}
            <th>{{header}}</th>
          {% endfor %}
        </tr>
      </thead>
      <tbody>
        {% for row in results %}
          <tr>
            {% for index in range(0, len(fieldnames)) %}
              <td>{{row[fieldnames[index]]}}</td>
            {% endfor %}
          </tr>
        {% endfor %}
      </tbody>
    </table>
  {% endif %}
 </div>
 </div>
</div>
</body>

and here is the error I get when I used to upload the file. Because both functions has the same POST request and when I click on submit button, it refers to the POST request which belongs to the textarea.

AttributeError
AttributeError: 'NoneType' object has no attribute 'split'

CodePudding user response:

From what you have posted this line is causing this particular issue:

user_csv = request.form.get('user_csv').split('\n')

I assume request.form is giving you a dict on which you are calling the get method.

get is a safe method for querying dict which has two parameters keyname and value.

All that being said, in case when your request.form doesn't contain 'user_csv' it will return the default value, which is None - thus the error:

AttributeError: 'NoneType' object has no attribute 'split'

Solution - send a complete request with all the parameters.

CodePudding user response:

You are right the error arises because you have two forms on the same page and your post request ends up empty. In general, is a common mistake to use multiple forms and submit buttons on the same Html page. Either split your forms into different Html pages or use the action attribute like this.

<form name="demo" action="/target_location" method="post">
  • Related