Support for PROJ 9.x+, including a brand new way of building the system using Dockerfiles
Slightly improves performances by using array-backed linked lists that are more cpu friendly on the cache
The license has been changed from LGPL to Mozilla Public License 2.0
Why
The current version of gocesiumtiler uses a built in version of Proj 4.9.2. While this version works, it is a decade old, cannot be updated / upgraded, brings some concerns in terms of thread safety and severely lags behind the modern versions of Proj in terms of supported projections.
Unfortunately, there are no go native libraries to perform coordinate conversion, hence the upgrade of Proj remains the only reasonable path forward to removing the dependency on Proj 4.9.2.
How
The upgrade from Proj4 to the newer Proj versions was not trivial. Proj4 was a self-contained, zero dependencies, C library, whereas the newer versions are C/C++ libraries with external dependencies, namely SQLite, Libtiff and CURL.
One of the main objectives of gocesiumtiler is to remain as much self contained as possible to maximize ease of use and portability. This means that the go code should be statically linked at build time with the Proj library and its dependencies, resulting in a single portable executable.
In order to achieve that, Proj had to be rebuilt statically from the sources for both the Windows and Linux x86-64 environments, which adds significant complexity to the project development setup.
In order to achieve reproducible builds, a Dockerfile has been added. This leverages multi-stage builds, mingw64 and vcpkg to cross build, under a linux environment, for both linux and windows.
For local development, a DEVELOPMENT.md file has been included which explains how to setup the dev environment in Windows, outside of Docker.
Backward incompatible changes
The CR introduces a few backward incompatible changes:
The -geoid flag in the CLI has been removed, and the geoid to ellipsoid utilities removed.
The reason for this change is that the code used for coordinate conversion was under LGPL, forcing this library also to be released under those terms. LGPL however doesn't fit well a go-based environment because the code in go statically builds with other code bases. The Mozilla Public License 2.0 instead is more appropriate as it limits the scope to the source files, encouraging contributions back to the project but not limiting commercial usage of the library embedded in other products. At this moment the even more permissive MIT license is not being considered, but could be in future.
Having said this, the vertical coordinate conversion now it's absorbed by the newer Proj library, which is capable of such conversions. The README.md has been updated to reflecct this.
The --epsg flag (and relative tiler parameter) is now a string and not just an integer.
This change allows users to specify combined CRS via supported Proj syntax like "EPSG:32633+3855" or via a Proj4 string or WKT text, giving much more flexibility to the too. The CLI is however still backward compatible as every number X will be considered equivalent to the string "EPSG:X"
Architectural changes
The major change is the introduction of a coordinate conversion factory function type. This is due to the fact that Proj Context instances cannot be shared across threads, hence different goroutines now need to have a way to initialize their own context.
Alternatively, mutex locking could have been used but this would have lead to severely degraded performances.
Development flow changes
The development flow is also changed. If before a simple go build command was sufficient, now first the developer has to compile statically the Proj library.
The DEVELOPMENT.md file has been added to clarify how to setup the development environment.
Additionally two build script, for linux and windows, have been added build.sh and build.ps1. These can be invoked and will use Docker to ensure reproducible builds without installing any dependency on the local system.
Limitations
Proj is built without CURL support:
This implies that users have to manually download extra grid files from the Proj CDN if they need them. The README.md has been updated accordingly. Support for CURL-enabled builds will be assessed in the future.
The share folder is externalized again.
While the assets were embedded in the binary in version 2.0.0-alpha and 2.0.0-beta, this CR externalises them again. The reason is that in order to have a path where to download the Proj Data downloaded from the CDN, the folderfor unzipping should be explicit, hence the decision has been to revert back the idea of embedding the resources. If CURL support is added, this might be changed back again in future.
What
This big CR adds three changes:
Why
The current version of gocesiumtiler uses a built in version of Proj 4.9.2. While this version works, it is a decade old, cannot be updated / upgraded, brings some concerns in terms of thread safety and severely lags behind the modern versions of Proj in terms of supported projections.
Unfortunately, there are no go native libraries to perform coordinate conversion, hence the upgrade of Proj remains the only reasonable path forward to removing the dependency on Proj 4.9.2.
How
The upgrade from Proj4 to the newer Proj versions was not trivial. Proj4 was a self-contained, zero dependencies, C library, whereas the newer versions are C/C++ libraries with external dependencies, namely SQLite, Libtiff and CURL.
One of the main objectives of gocesiumtiler is to remain as much self contained as possible to maximize ease of use and portability. This means that the go code should be statically linked at build time with the Proj library and its dependencies, resulting in a single portable executable.
In order to achieve that, Proj had to be rebuilt statically from the sources for both the Windows and Linux x86-64 environments, which adds significant complexity to the project development setup.
In order to achieve reproducible builds, a Dockerfile has been added. This leverages multi-stage builds, mingw64 and vcpkg to cross build, under a linux environment, for both linux and windows.
For local development, a DEVELOPMENT.md file has been included which explains how to setup the dev environment in Windows, outside of Docker.
Backward incompatible changes
The CR introduces a few backward incompatible changes:
-geoid
flag in the CLI has been removed, and the geoid to ellipsoid utilities removed.The reason for this change is that the code used for coordinate conversion was under LGPL, forcing this library also to be released under those terms. LGPL however doesn't fit well a go-based environment because the code in go statically builds with other code bases. The Mozilla Public License 2.0 instead is more appropriate as it limits the scope to the source files, encouraging contributions back to the project but not limiting commercial usage of the library embedded in other products. At this moment the even more permissive MIT license is not being considered, but could be in future.
Having said this, the vertical coordinate conversion now it's absorbed by the newer Proj library, which is capable of such conversions. The README.md has been updated to reflecct this.
--epsg
flag (and relative tiler parameter) is now a string and not just an integer. This change allows users to specify combined CRS via supported Proj syntax like "EPSG:32633+3855" or via a Proj4 string or WKT text, giving much more flexibility to the too. The CLI is however still backward compatible as every number X will be considered equivalent to the string "EPSG:X"Architectural changes
The major change is the introduction of a coordinate conversion factory function type. This is due to the fact that Proj Context instances cannot be shared across threads, hence different goroutines now need to have a way to initialize their own context.
Alternatively, mutex locking could have been used but this would have lead to severely degraded performances.
Development flow changes
The development flow is also changed. If before a simple
go build
command was sufficient, now first the developer has to compile statically theProj
library.The
DEVELOPMENT.md
file has been added to clarify how to setup the development environment.Additionally two build script, for linux and windows, have been added
build.sh
andbuild.ps1
. These can be invoked and will use Docker to ensure reproducible builds without installing any dependency on the local system.Limitations
share
folder is externalized again. While the assets were embedded in the binary in version2.0.0-alpha
and2.0.0-beta
, this CR externalises them again. The reason is that in order to have a path where to download the Proj Data downloaded from the CDN, the folderfor unzipping should be explicit, hence the decision has been to revert back the idea of embedding the resources. If CURL support is added, this might be changed back again in future.