How to make bootstrap-table-filter-control work with Flask, Jinja and Dataframe
After some back to basics step-by-step testing, I found my own solution and it's working like a charm now. My yield.html looks like this, with the bootstrap-table filter controls, search, and sorting enabled:
<head><!-- Required meta tags --><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"> <!-- Bootstrap CSS --><link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous"><link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.6.3/css/all.css" integrity="sha384-UHRtZLI+pbxtHCWp1t77Bi1L4ZtiqrqD80Kn4Z8NTSRyMA2Fd33n5dQ8lWUE00s/" crossorigin="anonymous"><link rel="stylesheet" href="https://unpkg.com/bootstrap-table@1.16.0/dist/bootstrap-table.min.css"> <link rel="stylesheet" type="text/css" href="http://cdnjs.cloudflare.com/ajax/libs/bootstrap-table/1.16.0/extensions/filter-control/bootstrap-table-filter-control.css"> </head> <body> <div class="container"> <table id="table" data-toggle="table" data-filter-control="true" data-show-search-clear-button="true" data-sortable="true" classes="table-sm" data-pagination="true" data-show-columns="true" data-show-columns-toggle-all="true" class="table-responsive"> <thead> <tr> <!--special characters and spaces not allowed in data-field name--> <th data-field="columnA" data-filter-control="input" data-sortable="true">column A</th> <th data-field="columnB" data-filter-control="select" data-sortable="true">column B</th> <th data-field="columnC" data-filter-control="input" data-sortable="true">column C</th> </tr> </thead> <tbody> {% for row in tableA %} <tr> <!--special characters and spaces not allowed in data-field name--> <td>{{ row.columnA }}</td> <td>{{ row.columnB }}</td> <td>{{ row.columnC }}</td> </tr> {% endfor %} </tbody> </table> </div> <!-- Optional JavaScript --> <!-- jQuery first, then Popper.js, then Bootstrap JS --> <script src="https://code.jquery.com/jquery-3.3.1.slim.min.js" integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo" crossorigin="anonymous"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"></script> <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script> <script src="https://unpkg.com/bootstrap-table@1.16.0/dist/bootstrap-table.min.js"></script> <script src="https://unpkg.com/bootstrap-table@1.16.0/dist/extensions/filter-control/bootstrap-table-filter-control.min.js"></script></body></html>
Notably, instead of calling an entire table that was made by to_html (dataframe to complete html table with header and row tags included) in the main.py app, I have to specify the table header specifically (within thead tags) with each column's parameters stated clearly, and no spaces and special characters allowed in the data-field name of header, and then to pull in the data rows using the {% for row in tableA %} with the corresponding column names.
In my python app, my data was from a dataframe, which I would need to convert to a python data type, specifically python dictionary that is list like, using data = df.to_dict('records')
And when i render the template, I can pass this dictionary over to the template using return render_template('yield.html', tableA = data)
My python app route looks like this:
@app.route('/')def hello(): data = df.to_dict('records') return render_template('yield.html', tableA = data)
A simple example of use bootstrap-table and flask.
Structure:
├── app.py└── templates └── table.html
Table.html:
<!DOCTYPE html><html><head> <meta http-equiv="content-type" content="text/html; charset=UTF-8"> <meta name="robots" content="noindex"> <title>Bootstrap Table - Flask example </title> <script src="https://code.jquery.com/jquery-2.2.4.min.js" integrity="sha256-BbhdlvQf/xTY9gja0Dq3HiwQF8LaCRTXxZKRutelT44=" crossorigin="anonymous"></script> <script type="text/javascript" src="http://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js"></script> <link rel="stylesheet" type="text/css" href="http://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css"> <link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-table/1.11.1/bootstrap-table.min.css"> <script type='text/javascript' src="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-table/1.11.1/bootstrap-table.min.js"></script> <style type='text/css'> .row-index { width: 50px; display: inline-block; } </style> <script type='text/javascript'> $(window).load(function(){ var data = {{data|tojson}}; var columns = {{columns|tojson}}; $(function() { $('#table').bootstrapTable({ data: data, columns: columns, }); }); }); </script></head><body> <div class="container" style="padding: 10px; "> <h1>{{title}}</h1> <br/> <div id="toolbar"></div> <table id="table" data-toggle="true" data-toolbar="#toolbar" data-search="true" data-show-columns="true" data-pagination="true" data-height="500"> </table> </div></body></html>
app.py:
from flask import Flask, render_templateimport json"""A example for creating a Table that is sortable by its header"""app = Flask(__name__)data = [{ "name": "bootstrap-table", "commits": "10", "attention": "122", "uneven": "An extended Bootstrap table"}, { "name": "multiple-select", "commits": "288", "attention": "20", "uneven": "A jQuery plugin"}, { "name": "Testing", "commits": "340", "attention": "20", "uneven": "For test"}]# other column settings -> http://bootstrap-table.wenzhixin.net.cn/documentation/#column-optionscolumns = [ { "field": "name", # which is the field's name of data key "title": "name", # display as the table header's name "sortable": True, }, { "field": "commits", "title": "commits", "sortable": True, }, { "field": "attention", "title": "attention", "sortable": True, }, { "field": "uneven", "title": "uneven", "sortable": True, }]#jdata=json.dumps(data)@app.route('/')def index(): return render_template("table.html", data=data, columns=columns, title='Flask Bootstrap Table')if __name__ == '__main__': #print jdata app.run(debug=True)
Reference: bambooom