In last couple of weeks, I experimented a lot with flask and web development. Since this a learning phase, I tend to setup lots of small projects, where a couple of external libraries (such as bootstrap or jQuery) usually need to be downloaded. As I am rather lazy, using an external tool (bower) to download those seemed a great idea.

Bower web page describes this tool as a “package manager for the web”. With bower you can easily search and download dozens of packages needed for web development. On the python side of things, there is a Flask-Bower package, which easies inclusion of bower downloaded files inside your flask project.

The method is fast and simple. Since it took me ridiculously long time to get this to work properly due to some stupid mistakes along the way, I thought it would be a good idea to describe the whole process and provide a repo with a working example.

Bower installation

The first thing, that I’ve found slightly confusing, was node.js installation (bower requirement). I’m using a LTS version of kubuntu (14.10), which has a couple of subtle issues interfering in a funny way.

Main node.js executable on ubuntu systems is not called node, but nodejs (ubuntu versions newer than 14.10 kept that convention). It turns out that executable name “node” was already taken, by a amatour packet radio related package. If you installed it by mistake (i.e. your full path to false node.js executable is /usr/sbin/node), the best thing to do in order to avoid confusion is to uninstall that package. Then all you need to be aware of is the different node.js executable naming, especially if you will update node.js with the ‘n’ tool, as described below.

The following steps summarize bower installation on ubuntu systems:

sudo apt-get install nodejs npm git

# Perform the following if your node.js version
sudo npm install -g n
sudo n lts      # installs lts node.js version
sudo n stable   # installs the latest stable node.js version
n               # select node version from the list, then hit enter 

# install bower
sudo npm install -g bower

If you also happen to use an archaic LTS distro, steps to install more up to date node.js version are also provided in the listing above. Installing node.js with ‘n’ may also be necessary if bower happens to expect node.js executable named node and not nodejs (I have no idea if it does, as I’m not a node.js expert).

Bower usage

The use of bower with flask is rather simple thanks to the Flask-Bower package. First, you need to install desired package with bower:

bower search bootstrap
bower search jquery
bower install jquery

First two commands will search through bower package index for bootstrap and jquery respectively (note the appearance of the ‘non-official’ packages in the search results).

The last command creates a bower_components directory and downloads needed files for jQuery. In case of packages with external dependencies (e.g. bootstrap, depending on jQuery), bower will automatically install those as well.

You can also request a specific version of a package:

bower install jQuery#2.1.4
bower install jQuery#2.1    # installs 2.1.4
bower install jQuery#2      # installs 2.2.4

As you can see in the example above, partial version numbers are also allowed. In such case, bower determines the latest minor version itself.

Use bower in flask project with Flask-Bower

In order to use files downloaded with bower in your flask project you can decide to do one of the following:

  • Move all necessary js/css/other files into ‘static’ directory manually
  • Create a route(s) yourself and utilize send_from_directory function to serve files from bower_components
  • Allow Flask-Bower to handle paths for you

Last two solutions are probably comparable. Since the one including Flask-Bower requires slighlty less work, I’ll describe it.

As usual, first thing to do is to install the package itself:

(venv):testflaskbower$ pip install Flask-Bower 

(note we are working inside virtualenv). Next, we need to make sure the bower_components directory (created when downloading packages with bower) is at the same level as ‘static’ and ‘templates’ directories:

├── bower_components
├── static
├── templates

Such structure allows for the simplest usage (note, that the location of the bower output directory location is configurable in Flask-Bower). Then all you have to do is to enable flask-bower in your project:

from flask import Flask
from flask_bower import Bower

app = Flask(__name__)

and use the url_for function with endpoint set to ‘bower.static’:

<script src="{{ url_for('bower.static', filename='jquery/dist/jquery.min.js') }}"></script>

That’s all! I think it’s worth stressing out how awesome this is – after installing bower on your system (done once) all you have to do in order to get external javascript libraries set up for your project is to invoke

bower install packagename

(optionally providing version), enable bower in your app (two lines of code) and reference needed files in your html templates with a proper target. So – no more manual downloads or searching through cdns.

As I said at the beginning, getting Flask-Bower to work took me ridiculously long time due to some stupid mistakes (and node.js installation issues on old ubuntu release). This git repository provides a working example with no moving parts – just clone it and run the application (full setup instructions in the repo). The file served with Flask-Bower (jquery.js) is also included in the repository (it was downloaded earlier using bower, so directory structure is same as you would get by running bower yourself). Hope that helps 🙂

Multiprocessing - understand your exception

  1. Looked at your repo in github – where is your “bower.json”? Does it need to be on the same level as the bower components or in the upper/outer application level?

Leave a Reply

Your email address will not be published.