Lesson 5: Exporting a GeoTIFF with Allmaps CLI
In this lesson we will download a IIIF image to our local machine, download the IIIF georeference annotation from Allmaps, and use command line tools to generate a Cloud-Optimized GeoTIFF to use in GIS.
This lesson focuses on one Allmaps CLI workflow: GeoTIFF export. We will use the CLI for other advanced workflows in the next lessons.
Before starting, make sure you have completed Lesson 4: Command Line Setup or already have the required tools installed.
Command line setup Next CLI workflow: GeoJSON overlay đšď¸ Have fun instead
Generating a GeoTIFF using Allmaps CLI
In this section, you will generate a georeferenced Cloud Optimized GeoTIFF (COG) from an Allmaps annotation.
This format is commonly used for web maps and allows efficient access to large raster datasets.
For an introduction to COGs and how they enable efficient, web-based access to raster data, see https://cogeo.org/.
For the main walkthrough, this example exports a GeoTIFF from the 1821 AGSL map of Paris used in the next two lessons. It is helpful to keep a record of the URLs for the resources you are working with, particularly if you are using an example other than the one provided.
Paris Example
| Resource | Location / URL |
|---|---|
| AGSL Map of Paris, 1821 | https://collections.lib.uwm.edu/digital/collection/agdm/id/1550/ |
| IIIF Manifest URL | https://collections.lib.uwm.edu/iiif/info/agdm/1550/manifest.json |
| Georeference annotation | https://annotations.allmaps.org/images/adeae8a56aaf59fb |
| Allmaps Image ID | adeae8a56aaf59fb |
| Image ID URL | https://cdm17272.contentdm.oclc.org/iiif/2/agdm:1550 |
| Image Dimensions | 10784 x 6941 |
| Expected Image Filename | adeae8a56aaf59fb.jpg |
The public item page and manifest use collections.lib.uwm.edu.
The IIIF Image API URL used by Allmaps is the canonical cdm17272.contentdm.oclc.org URL.
Use that image service URL in the command-line steps below so the generated filenames match the Allmaps annotation.
1. Create a Working Directory
Create a new directory for your image to keep it isolated from other images as you practice generating GeoTIFFs from Allmaps.
mkdir -p ~/allmaps/agsl-paris
cd ~/allmaps/agsl-paris
2. Download the Georeference Annotation
curl -L "https://annotations.allmaps.org/images/adeae8a56aaf59fb" -o annotation.json
If you are using a different map, use the annotation for that map instead. You can confirm that the annotation is readable with:
allmaps annotation parse annotation.json
3. Download the IIIF Image
GeoTIFF export is fussier than the GeoJSON workflow because the generated script expects local image filenames and source-image dimensions to match the Allmaps annotation.
allmaps fetch full-image "https://cdm17272.contentdm.oclc.org/iiif/2/agdm:1550"
ls -lh *.jpg
For this example, the downloaded file should be named adeae8a56aaf59fb.jpg.
If your file has a different name, rename it before continuing:
mv current-filename.jpg adeae8a56aaf59fb.jpg
Warning:
Unless you are working with the same map, your filename will be different. What matters is that the local image filename matches what the generated script expects.
By default, allmaps fetch full-image may not download the highest-resolution version.
To see which sizes the IIIF server can provide, inspect the image service metadata:
curl -s https://cdm17272.contentdm.oclc.org/iiif/2/agdm:1550/info.json | jq '.sizes'
For this example, the largest size listed should be 10784 x 6941, matching the dimensions in the Allmaps annotation.
If your local JPEG is smaller than the largest size, it will not match the pixel coordinates in the Allmaps annotation.
In that case, use dezoomify-rs to download the full-resolution image:
dezoomify-rs "https://cdm17272.contentdm.oclc.org/iiif/2/agdm:1550" full.jpg
mv full.jpg adeae8a56aaf59fb.jpg
4. Generate the GeoTIFF Script
cat annotation.json | allmaps script geotiff > paris_geotiff.sh
This will generate a shell script file paris_geotiff.sh that you will run soon.
The generated script expects a specific filename. If yours differs, it will fail.
5. Edit the Script
Open the script in VS Code or your text editor of choice:
# Visual Studio Code:
code paris_geotiff.sh
# nano
nano paris_geotiff.sh
#etc.
Look for this gdalwarp block:
gdalwarp \
-of COG -co COMPRESS=JPEG -co QUALITY=75 \
-dstalpha -overwrite \
-r cubic \
-cutline ./adeae8a56aaf59fb_2543dadd9c2fa8b1.geojson -crop_to_cutline -cutline_srs "EPSG:4326" \
-s_srs 'EPSG:3857' \
-t_srs 'EPSG:3857' \
-ts 9819 6706 \
-order 1 \
./adeae8a56aaf59fb_2543dadd9c2fa8b1.vrt \
./adeae8a56aaf59fb_2543dadd9c2fa8b1-warped.tif
This command uses gdalwarp to apply the georeferencing from the annotation and generate a georeferenced raster.
Before running the script, check whether you need to edit it. With current versions of GDAL, the generated script may run as-is. However, editing the script is still useful when you need compatibility with older GDAL versions or want to set processing options such as memory limits.
For older GDAL versions: remove the -cutline_srs flag.
The -cutline_srs option was added in GDAL 3.9, so scripts that include it may fail on earlier GDAL installations.
Before:
-cutline ./adeae8a56aaf59fb_2543dadd9c2fa8b1.geojson -crop_to_cutline -cutline_srs "EPSG:4326" \
After:
-cutline ./adeae8a56aaf59fb_2543dadd9c2fa8b1.geojson -crop_to_cutline \
Optional performance tuning: if you have sufficient available memory (RAM), you can speed up processing by adding -multi -wm 2048.
On low-memory systems, this may cause the command to fail.
If you are using a current GDAL version and only want to tune performance, you can leave -cutline_srs "EPSG:4326" in place and add -multi -wm 2048 on the next line.
Each line in a multi-line command must end with \, except the final line.
If a line is missing \, the command will terminate early and cause errors such as command not found or No target filename specified.
If you remove -cutline_srs and add the memory options, your updated gdalwarp command block should read like this:
gdalwarp \
-of COG -co COMPRESS=JPEG -co QUALITY=75 \
-dstalpha -overwrite \
-r cubic \
-cutline ./adeae8a56aaf59fb_2543dadd9c2fa8b1.geojson -crop_to_cutline \
-multi -wm 2048 \
-s_srs 'EPSG:3857' \
-t_srs 'EPSG:3857' \
-ts 9819 6706 \
-order 1 \
./adeae8a56aaf59fb_2543dadd9c2fa8b1.vrt \
./adeae8a56aaf59fb_2543dadd9c2fa8b1-warped.tif
Save the script file:
VS Code: File > Save or Ctrl+S to save.
nano: Ctrl+O to save, Enter to confirm the filename, Ctrl+X to exit nano.
Note:
There is an issue related to the
-cutline_srsflag on the Allmaps repository.
6. Run the Script
bash paris_geotiff.sh
If the script runs successfully, the output file is now georeferenced using the control points from the Allmaps annotation.
Warning:
Troubleshooting script failures and errors:
- See the âDownload the IIIF Imageâ step if your image size is wrong.
- Ensure you have made the appropriate adjustments in the generated shell script in the âEdit the Scriptâ step above. Regenerate the script to start over if you need to.
- Triple check your filenames and ensure they match what the shell script expects.
7. Verify the Output with GDAL
gdalinfo *-warped.tif
Check for the following in the output:
EPSG:3857- confirms the map is in Web MercatorSize is ...- shows the pixel dimensions of the output imageLAYOUT=COG- confirms the file is a Cloud Optimized GeoTIFF
You do not need to understand the full output; just confirm these values appear.
You have now generated a georeferenced GeoTIFF from an Allmaps annotation. This file can be used in GIS software or served as a web-accessible raster.