Project Layout and Webpack Configuration
In the previous post, we introduced concepts around deploying front-end assets. If you haven't read it and are not knowledgeable in this area, we suggest you read it now.
In this post, we'll describe the basic file structure of our project and dive into our Webpack configuration.
Before we dig in, I want to share my full video presentation from DjangoCon, the inspiration for this blog series. Enjoy!
When building complex applications, we find that by building small, contained units of logic representing the main features of our application, we can develop more stable, easy-to-maintain software. However, to execute and run these files, the client's browser needs all the files together to make sense of things. To further complicate matters, these small modules depend on each in a complex pattern.
Webpack builds a bundle using a configuration file that describes everything needed to build the bundle including the inputs (our files), options for translating the SASS and ES2015 files and other configuration pieces, e.g. how to name output files.
There are many posts dedicated to beginning Webpack and we'd prefer to link to them rather than recreate them.
- Webpack's official page for installation
- Beginner's Guide to Webpack
- Webpack's Getting Started Tutorial
A note on Webpack configuration
Configuring Webpack is a complex task. This is the configuration we've settled upon over the past year and it may not work for your project. We hope this configuration will help you find the specific implementation that works for your team.
First, here is the (heavily redacted :)) directory layout of our main application:
bundle.js that effectively serves as our Webpack config file.
Finally, an example app-specific config file:
bundle.js is our main entry point into the bundle build process. It specifies the shared plugins we use to control the bundle build process and specifies different plugins whether we're building for development or production.
The key differences between dev and production builds is what happens to the bundle afterwards. Most importantly, we extract the CSS out of the bundle into a separate CSS file (using the ExtractTextPlugin) and remove all whitespace from the bundle (using the webpack.optimize.UglifyJS plugin).
app.webpack.config.js specifies application-specific plugins and entry points into a particular part of our site. We currently have 5 different bundles that drive different areas of our application. We've found this allows us to produce small bundles and share common functionality where needed.
To build a particular bundle, we execute
$ NODE_ENV=production node bundle --config app.
When running a Webpack build, we track the process using the webpack-bundle-tracker plugin. This Webpack plugin produces a small JSON file that describes the state of the most recent Webpack build. This file is very important to how we integrate Webpack-generated bundles with the rest of our Django application.
In the next few posts, we'll describe how we tie all this into our main Django application and a few little niceties we've built into our deployment process to help our team be as confident as possible we deploy new features to our customers.
Article by Scott Burns, VP of Engineering for Stratasan