Webpack + Cesium sample project published

I’ve been working on a prototype project that uses Webpack for the bundling/build process, and includes Cesium. I’m building the UI with React, managing data with Redux, and using Mocha to run my tests offline under Node. I’ve managed to accumulate a number of useful and interesting bits of configuration during this effort, and wanted to make my working project available as a reference for anyone else interested.

The repository is available at https://github.com/markerikson/react-redux-cesium-testing-demo .

Pasting from my README:

This sample project demonstrates demonstrates several things:

  • Application code using React and Redux, with bare-basic usage of loading images and CSS

Use of the Cesium 3D globe library, inside a React component, installed
using NPM, and with the Cesium pre-built assets served directly from /node_modules/cesium/ instead of requiring a copy step during development

  • Webpack configuration using a “base” set of config options, and multiple extensions of that for development, production, offline test execution, and live test execution in a browser
  • Test configuration using Mocha+JSDOM+Chai+Sinon+Enzyme, allowing execution of
    React component unit tests in a Node environment without the need for Karma or a browser
  • Basic ESLint configuration for style checking

Use of the https://github.com/JamieMason/shrinkpack tool for committing dependencies with minimal overhead, thus allowing dependable and repeatable installations while minimizing the risk of being affected by problems like NPM-Left-Pad-Gate

  • Creation of a React component that is loaded asynchronously and rendered when it becomes available

I used https://github.com/mmacaula/cesium-webpack as a reference while putting this together, but was able to advance the approaches suggested there by figuring out how to serve Cesium’s files directly from the installed NPM package. Also note that I was able to create a React component that renders a Cesium.Viewer and another that manages a BillboardCollection, and I can successfully run tests on the second component under Node (running anything that actually instantiates a Cesium.Scene is a bad idea, as WebGL is obviously not available).

Hopefully this sample is useful to someone!

Mark Erikson

Great! Thanks Mark! We tweeted about it and we’re going to mention this in the news section of the blog post for the upcoming Cesium 1.20 release.

Best,

Hannah

Cool. As I mention in the readme, this is purely a prototype that I’ve been working on. Had a few people ask me to show my working test config, and I definitely wanted to demo my Cesium+Webpack integration as well, so I just quickly stripped out anything related to the actual app I’d been prepping for. Certainly not intended for production use, but the configuration that’s in there should work.

I’m happy to answer questions on how the configuration works, either here or on Github.

Update: I think I have just successfully managed to figure out a much better way to load Cesium with Webpack, using Webpack’s “DllPlugin” and “DllReferencePlugin”. I need to do some further testing, experimentation, and cleanup, but at the moment it looks like it worked. And, best as I can tell, I get faster builds, AND complete sourcemaps for all of Cesium’s original source files - I was able to stick a breakpoint in CesiumWidget.js’s resizing code.

I will post another update once I’ve managed to get this cleaned up, and also update the sample repo as well.

Took me a couple weeks to find the time, but I was able to push some updates to my sample project at https://github.com/markerikson/react-redux-cesium-testing-demo.

Rather than referencing the Cesium source directly in my app, or trying to reference the pre-built Cesium.js file, I now have a separate Webpack configuration that I use to pre-compile Cesium itself, using Webpack’s “DllPlugin”. This generates a bundled Cesium.js file that is effectively the same as the one produced by Cesium’s own build process, but also includes a sourcemap, plus a metadata file describing the contents of the bundle. I can then reference this “DLL” file in my application’s actual Webpack config. Webpack then simply parses the metadata from that “DLL” output, and knows where to find all the Cesium code that my app needs. That means it doesn’t have to do any additional parsing of Cesium’s source while building my application, making build times faster. Also, the sourcemap generated from the DLL build allows me to actually debug into Cesium itself while working on my app, even though the page is loading that bundled Cesium.js file.

In addition, in my actual work project, I’ve successfully been able to build a number of React components that manage the lifetime of Cesium primitives and render them on the globe. I updated the sample project with a component that demonstrates that technique. I also have been able to write a bunch of unit tests at work that exercise my React+Cesium components offline under Node, and updated the sample project with a small demonstration of that too.

I am unfortunately limited in what I can actually share, but hopefully this project serves as enough proof of concept to demonstrate the techniques I’ve been able to put together. I’d be happy to answer any questions if anyone would like to know more.

Mark Erikson