Composing spatial data interfaces with javascript | XYZ

Dennis Bauszus
Feb 27, 2019 · 5 min read defines composition as the act of combining parts or elements to form a whole.

Ever since reading Eric Elliot’s series on software composition (now a book) I have meant to implement these practices into the development of GEOLYTIX’ open source mapping framework XYZ. However, the pressure to provide a working solution asap meant that many ideas could not be fully realized until now with many more key features to be rolled out in the future. As Eric states in his article: I learned the essence of software design far too late in life. I do believe we are in good company here.

Labeled as an open source web mapping framework for the serverless cloud I tend to use the term ‘spatial data interface’ these days. Even more so do I like to think about software composition as opposed to simply writing code. Truth be told; a majority of XYZ’ working components are not directly written by our team at GEOLYTIX. Not to prepare copypasta, using the best available libraries is quintessential for the enduring success of open source in spatial analysis.

As a bare minimum some middleware is required to satisfy secure access from a distributed client application to the spatial data at rest. Being an opinionated system, all data sources will be in PostgreSQL which facilitates the spatial capabilities of its PostGIS extension.

The client will be a browser with an engine that is capable to execute ES6+ javascript. We have a preference for the Fastify web framework to manage our middleware routes and security. XYZ’s token security itself being a huge topic which demands its own article. 👉 Watch this space.

Built with Fastify; XYZ is a restful spatial API which may evaluate signed token, query connected data sources and respond with formatted data for presentation in map or table components. As an interface XYZ allows the execution of SQL scripts to create, analyse (mostly aggregate) and update spatial data.

Workspaces / Locales / Layer / Locations

In XYZ, spatial data is defined as a workspace which is loaded in the middleware and in the client. Workspaces may be divided into several locales. Each locale has a unique set of layers which provide information about the locations which it is comprised of.

With the locale, layer and table it is possible to get data from the geojson endpoint of a deployment which has the workspace and matching data source connections loaded into memory. This example link will load GEOLYTIX office locations.

Locations are the query-able features which a layer comprises. The select by id endpoint for example can be used to get a JSON for GEOLYTIX’ London office.

A complete list of routes and their parameters is outlined in the XYZ Developer documentation.

XYZ Control

The XYZ control library, bundled up with Webpack is hosted as a static file with every XYZ deployment. Once loaded the library will attach a _xyz() method to the window object.

Without a callback _xyz() will asynchronous load a workspace from the XYZ host and return an instance of the XYZ control.

Thereafter it is possible to create map or table views which interact with the XYZ API.

_xyz.mapview.create() will create a map view in a specified container.

Clicking on a cluster will display the location view for the selected location in a popup.

A layer can also be displayed as table. For this spatial data interface it is not required to create a mapview.

Composing dashboards with controls

A dashboard is the combination of multiple control views and methods. For the next example we create a fiddle with a map control and corresponding table view. Scroll zoom is enabled on this map view and the table will update to the current viewport of the map.

_xyz.mapview.changeEnd = _xyz.utils.compose(
() => _xyz.tableview.current_table.update()

We use function composition to add the update method of the map after the execution of the changeEvent of the Leaflet map object.

More complex dashboards can be created by controlling the behavior of XYZ control methods.

The last example adds zoom button which are wired to the map control during the initialization. The location view for the currently selected location is presented in a container next to the map. The United Kingdom will be programmatically selected after the map control has been initialized.

We also wire a button which updates a location. This allows to use the inputs in the location view to change location values. Updating the location will refresh the map. Making use of dynamic vector tiles, changed population values which are reflected in the theme will be colored in after the location has been updated.

Making use of the complete range of XYZ control methods we are able to construct more advanced dashboards.

Schema for default XYZ dashboard.

The default dashboard is returned on the root path of every XYZ instance. Using URL hooks it is possible to control the initial view and selection of locations in the default dashboard.…

Using XYZ’s compose utility we are able to arrange multiple location and layer views in list controls. = _xyz.utils.compose(, ()=>{ = 'block';  layer.toggle.textContent = 'layers';  // Push the layer into the layers hook array.  _xyz.hooks.push('layers', layer.key);  // Check whether other group layers are visible.
if ( {


Dashboards may also be used to create PDF reports. Which is what we are currently working on. Then there are location tables to be shown very soon.

And while Leaflet brought us here we are now stretching the capabilities of the Leaflet.Vectorgrid plugin.

We are planning to fork XYZ with OpenLayers for the map control or may try to use the Tangram plugin which has shown great promise with HERE XYZ.

On that note. We really love what the HERE devs are doing. 👏

While similar in name and nature, our project is not related to HERE XYZ.

We really appreciate you taking the time and read this brief introduction. I am planning on presenting at FullStackConf# London and at FOSS4G in Bucharest later this year. Better documentation and workshops will be available soon. Promise.

This is where you come in… Contributions in any form are more than welcome. This can be comments, forks, deployments, questions. Please meet us at conferences or even send us your CV.

We are always looking for talented people to join our team.

For all inquiries mail to:


A collection of articles written by the GEOLYTIX team.