CLI reference¶
Generated from lunar <command> --help when the docs are built.
| Command | Purpose |
|---|---|
build-db |
Build the local Parquet index database(s). |
download |
Download LROC image files to a local directory. |
query |
Print metadata for LROC NAC images from the Parquet index. |
search |
Find images whose footprint intersects a box, point+radius or AOI polygon (local index). |
ode-search |
Search lunar products (ShadowCam, LROC NAC, Kaguya TC) via the ODE REST API. |
pairs |
Rank NAC stereo pairs (or select SfS images with --sfs) over a box, point+radius or AOI polygon. |
reference |
Reference data for the Artemis III regions: crop windows, PGDA LOLA 5 m DEMs, Bertone SfS DEMs. |
process |
Run the ISIS + GDAL pipeline on LROC NAC images. |
kaguya |
Download Kaguya TC / MI images and import them into ISIS (cube + CSM camera). |
shadowcam |
Download ShadowCam cubes, spiceinit them and write CSM cameras for ASP. |
stereo |
Build a DEM from a NAC stereo pair (bundle_adjust, parallel_stereo, point2dem). |
sfs |
Build a shape-from-shading DEM from NAC images and a prior DEM (ISIS + ASP). |
sfs-report |
Metrics, figures and an HTML report of an SfS work dir (Bertone et al. 2026 validation). |
workspace |
Query a work dir's DuckDB workspace (images, pairs, bundle-adjustment tables and views). |
serve |
Serve the Lunar Toolkit web app with local parquet files. |
app |
Open the Lunar Toolkit web app in a desktop window. |
lunar¶
usage: lunar [-h] [-v]
{build-db,download,query,search,ode-search,pairs,reference,process,kaguya,shadowcam,stereo,sfs,sfs-report,workspace,serve,app} ...
Lunar imagery toolkit - build LROC index databases, search footprints, query ODE (ShadowCam, LROC, Kaguya TC and MI), download and import images into ISIS, build stereo and shape-from-shading DEMs with ISIS + ASP, and fetch Artemis III reference data.
positional arguments:
{build-db,download,query,search,ode-search,pairs,reference,process,kaguya,shadowcam,stereo,sfs,sfs-report,workspace,serve,app}
build-db Build the local Parquet index database(s).
download Download LROC image files to a local directory.
query Print metadata for LROC NAC images from the Parquet index.
search Find images whose footprint intersects a box, point+radius or AOI polygon
(local index).
ode-search Search lunar products (ShadowCam, LROC NAC, Kaguya TC) via the ODE REST
API.
pairs Rank NAC stereo pairs (or select SfS images with --sfs) over a box,
point+radius or AOI polygon.
reference Reference data for the Artemis III regions: crop windows, PGDA LOLA 5 m
DEMs, Bertone SfS DEMs.
process Run the ISIS + GDAL pipeline on LROC NAC images.
kaguya Download Kaguya TC / MI images and import them into ISIS (cube + CSM
camera).
shadowcam Download ShadowCam cubes, spiceinit them and write CSM cameras for ASP.
stereo Build a DEM from a NAC stereo pair (bundle_adjust, parallel_stereo,
point2dem).
sfs Build a shape-from-shading DEM from NAC images and a prior DEM (ISIS +
ASP).
sfs-report Metrics, figures and an HTML report of an SfS work dir (Bertone et al.
2026 validation).
workspace Query a work dir's DuckDB workspace (images, pairs, bundle-adjustment
tables and views).
serve Serve the Lunar Toolkit web app with local parquet files.
app Open the Lunar Toolkit web app in a desktop window.
options:
-h, --help show this help message and exit
-v, --verbose Enable DEBUG-level logging.
lunar build-db¶
usage: lunar build-db [-h] [--all] [--force] [--update] [--release VOLUME] [--volume-only] [--wkt]
[--memory-limit SIZE] [--threads N] [--data-dir DIR] [--cache-dir DIR]
[DATASET ...]
positional arguments:
DATASET Datasets to build: edr, cdr, rdr (default: edr if none given).
options:
-h, --help show this help message and exit
--all Build all three datasets: edr, cdr, rdr.
--force Rebuild even if the Parquet already exists.
--update Append newer per-volume INDEX.TABs to an existing database.
--release VOLUME Build from this PDS volume, e.g. LROLRC_0066C (default: newest on the
server).
--volume-only Use the volume's own INDEX/INDEX.TAB instead of the cumulative
CUMINDEX.TAB.
--wkt Also store an FP_WKT footprint polygon column.
--memory-limit SIZE DuckDB memory limit; sorting spills to disk beyond it (default: 4GB).
--threads N DuckDB worker threads (default: all cores).
--data-dir DIR Where to write Parquet files (default: LUNAR_DATA_DIR or the user data
dir).
--cache-dir DIR Where to cache raw TAB/LBL downloads (default:
/home/runner/.cache/lunar_toolkit).
Examples
--------
lunar build-db # EDR only (default)
lunar build-db edr cdr # EDR and CDR
lunar build-db --all # EDR, CDR, and RDR
lunar build-db edr --force # rebuild even if exists
lunar build-db edr --update # append PDS volumes newer than the built release
lunar build-db edr --release LROLRC_0066C --volume-only # one volume (~20k rows)
lunar download¶
usage: lunar download [-h] [--from-file FILE] [--output-dir DIR] [--dataset {edr,cdr}] [--force]
[--workers N] [--data-dir DIR]
[SOURCE ...]
positional arguments:
SOURCE Product IDs (e.g. M1096757719LE) or PDS URLs.
options:
-h, --help show this help message and exit
--from-file FILE Text file of product IDs or URLs, one per line (#comments ignored).
--output-dir DIR Destination directory (default: current working directory).
--dataset {edr,cdr} Download each image's raw EDR or calibrated CDR file (default: edr); IDs
are looked up in the index matching their LE/RE or LC/RC suffix.
--force Download again even if the file exists.
--workers N Parallel download workers (default: 8).
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar download M1096757719LE M1096757719RE
lunar download M1096757719LE --output-dir ./raw
lunar download --from-file ids.txt --output-dir ./raw
lunar download https://pds.lroc.im-ldi.com/data/.../M1096757719LE.IMG
lunar download M1096757719LC --dataset cdr # CDR image
Files already in --output-dir are skipped (use --force to download them again);
interrupted downloads resume from their .part file.
lunar query¶
usage: lunar query [-h] [--from-file FILE] [--data-dir DIR] [SOURCE ...]
positional arguments:
SOURCE Product IDs, local .IMG paths, or a text file of IDs.
options:
-h, --help show this help message and exit
--from-file FILE Text file of product IDs or paths, one per line.
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar query M1096757719LE
lunar query M1096757719LE M1096757719RE
lunar query --from-file ids.txt
lunar query /path/to/M1096757719LE.IMG
lunar search¶
usage: lunar search [-h] [--dataset {edr,cdr}] (--bbox WEST SOUTH EAST NORTH | --point LAT LON |
--aoi FILE_OR_WKT) [--radius-km KM] [--inc MIN MAX] [--emi MIN MAX]
[--phase MIN MAX] [--nac-only] [--limit N] [--csv FILE] [--wkt]
[--data-dir DIR]
options:
-h, --help show this help message and exit
--dataset {edr,cdr} Index to search (default: edr).
--bbox WEST SOUTH EAST NORTH
--point LAT LON
--aoi FILE_OR_WKT Area of interest: GeoJSON / WKT file or WKT polygon string.
--radius-km KM
--inc MIN MAX Incidence angle range.
--emi MIN MAX Emission angle range.
--phase MIN MAX Phase angle range.
--nac-only Only NAC products.
--limit N
--csv FILE Write matching rows to CSV.
--wkt Include an FP_WKT footprint column.
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar search --bbox 0 -90 360 -85 --nac-only --inc 80 95
lunar search --bbox 355 -5 5 5 # crosses the 0/360 seam
lunar search --point -89.67 129.8 --radius-km 15 --csv shackleton.csv
lunar search --aoi aoi.geojson --nac-only # QuickMap-exported polygon
lunar search --aoi "POLYGON((350 -5, 10 -5, 10 5, 350 5, 350 -5))"
--bbox is WEST SOUTH EAST NORTH (degrees, positive east; WEST > EAST crosses 0/360).
--aoi takes a GeoJSON / WKT file or a WKT string (lon lat, degrees, positive
east); bbox matches are refined by exact polygon intersection.
lunar ode-search¶
usage: lunar ode-search [-h] [--instrument INSTRUMENT] [--product-type PT]
[--bbox WEST SOUTH EAST NORTH | --point LAT LON | --aoi FILE_OR_WKT]
[--radius-km KM] [--inc MIN MAX] [--emi MIN MAX] [--phase MIN MAX]
[--time START END] [--limit N] [--count] [--csv FILE] [--download DIR]
[--kind KIND] [--match TEXT] [--workers N]
options:
-h, --help show this help message and exit
--instrument, -i INSTRUMENT
Instrument: shadowcam, lroc, kaguya_tc, kaguya_mi (default: shadowcam).
--product-type, -t PT
Product type alias or ODE pt code (default: instrument's default).
--bbox WEST SOUTH EAST NORTH
Bounding box in degrees.
--point LAT LON Search around a point (use with --radius-km).
--aoi FILE_OR_WKT Area of interest: GeoJSON / WKT file or WKT polygon string.
--radius-km KM Radius for --point (default: 1 km).
--inc MIN MAX Incidence angle range.
--emi MIN MAX Emission angle range.
--phase MIN MAX Phase angle range.
--time START END Observation time range (UTC, e.g. 2023-01-01 2023-12-31).
--limit N Maximum number of products to return (default: 200).
--count Only print the number of matches.
--csv FILE Write results (common schema) to CSV.
--download DIR Download the selected files to DIR.
--kind KIND Files to download: product, label, browse, referenced, derived, all.
--match TEXT Only download files whose name contains TEXT (e.g. _cog.tif).
--workers N Parallel download workers (default: 4).
Examples
--------
lunar ode-search --instrument shadowcam --bbox 0 -90 360 -89 --inc 80 90
lunar ode-search --instrument shadowcam --point -89.67 129.8 --radius-km 15
lunar ode-search --instrument lroc --product-type cdr --bbox 355 -1 5 1 --csv hits.csv
lunar ode-search --instrument shadowcam --point -89.67 129.8 --radius-km 5 \
--download ./shadowcam --kind product
lunar ode-search --instrument shadowcam --aoi aoi.geojson # QuickMap polygon
Product types - shadowcam: raw, cal, cmos, umos, dtm; lroc: edr, cdr; kaguya_tc: stereo, mono, dtm, ortho, morning, evening; kaguya_mi: vis, nir, vis2c, nir2c, l3c5, map
(raw ODE pt codes such as EDRNAC4 are accepted too).
--bbox is WEST SOUTH EAST NORTH, longitudes positive east; WEST > EAST crosses 0/360.
--aoi takes a GeoJSON / WKT file or a WKT string; ODE is queried with its bounding
box and footprints are then intersected with the polygon.
lunar pairs¶
usage: lunar pairs [-h] [--dataset {edr,cdr}] (--bbox WEST SOUTH EAST NORTH | --point LAT LON |
--aoi FILE_OR_WKT) [--radius-km KM] [--inc MIN MAX] [--emi-max DEG]
[--conv MIN MAX] [--max-inc-diff DEG] [--max-az-diff DEG] [--min-overlap FRAC]
[--sfs] [--az-bin DEG] [--per-bin N] [--max-images N] [--greedy] [--coverage]
[--views N] [--engine {auto,python,duckdb}] [--workspace DIR] [--top N]
[--csv FILE] [--list FILE] [--data-dir DIR]
options:
-h, --help show this help message and exit
--dataset {edr,cdr} Index to search (default: edr).
--bbox WEST SOUTH EAST NORTH
--point LAT LON
--aoi FILE_OR_WKT Area of interest: GeoJSON / WKT file or WKT polygon string.
--radius-km KM
--inc MIN MAX Incidence angle range.
--emi-max DEG Maximum emission angle.
--conv MIN MAX Convergence angle limits (default: 10 60).
--max-inc-diff DEG
--max-az-diff DEG Maximum sub-solar azimuth difference within a pair.
--min-overlap FRAC
--sfs Select illumination-diverse images instead of stereo pairs.
--az-bin DEG --sfs: azimuth bin width / minimum separation (default: 30).
--per-bin N
--max-images N
--greedy --sfs: enforce --az-bin separation between all picks instead of fixed
bins.
--coverage --sfs: per-location greedy selection over an AOI grid.
--views N --sfs --coverage: target distinct Sun azimuths per location (default: 3).
--engine {auto,python,duckdb}
Stereo pair engine (default: auto = duckdb from 300 images).
--workspace DIR Write the images and pairs tables to DIR/lunar.duckdb (implies --engine
duckdb).
--top N Rows to print (default: 30).
--csv FILE Write the full result to CSV.
--list FILE --sfs: write selected product IDs, one per line.
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar pairs --point -89.67 129.8 --radius-km 3 --top 20
lunar pairs --bbox 355 -5 5 5 --conv 15 45 --csv pairs.csv
lunar pairs --point -89.67 129.8 --radius-km 3 --sfs --inc 80 95 --list sfs_images.txt
lunar pairs --point -89.67 129.8 --radius-km 3 --sfs --coverage --views 3
lunar pairs --aoi aoi.geojson --sfs --coverage
lunar pairs --point -89.5 0 --radius-km 30 --engine duckdb --workspace work/pole
--bbox is WEST SOUTH EAST NORTH (degrees, positive east; WEST > EAST crosses 0/360).
--aoi takes a GeoJSON / WKT file or a WKT string (lon lat, degrees, positive east).
The search region is also the AOI that overlaps / coverage are measured in.
--sfs output (and --list) is sorted by sub-solar azimuth, as ASP SfS expects.
--engine duckdb ranks pairs with a DuckDB spatial self-join (same pairs and metrics as
the Python engine); auto uses it from 300 images when the spatial extension loads.
--workspace keeps the images and pairs tables in DIR/lunar.duckdb (see lunar workspace).
lunar reference¶
usage: lunar reference [-h] {list,show,crop,pgda,sdem} ...
positional arguments:
{list,show,crop,pgda,sdem}
list List the 13 regions.
show Show one region.
crop Print a square crop window centred on a region.
pgda Download a region's PGDA LOLA 5 m site files.
sdem List / download / extract a region's Bertone et al. Zenodo zip.
options:
-h, --help show this help message and exit
Examples
--------
lunar reference list
lunar reference show malapert # bbox, ROI projwin, PGDA site, Zenodo zip
lunar reference crop 11 --crop-km 2.5 # 2.5 km window at the ROI centre
lunar reference crop malapert --center -85.98 -0.26 --format wkt
lunar reference pgda malapert --kind surf toterr -o ref
lunar reference pgda malapert --kind clones --clones 10 -o ref
lunar reference pgda malapert --kind xyzi --csv --crop-km 2.5 -o ref
lunar reference sdem malapert --list # zip members (remote central directory)
lunar reference sdem malapert --remote --member GLDELEV GLDSIGM -o ref
lunar reference sdem malapert --download -o ref --member GLDELEV
REGION is an id (0-12), name, slug, unique part of a name or PGDA site
(11, "Malapert Massif", malapert-massif, malapert, Site23). The ROI is the
polar stereographic square the SfS DEM covers (= the PGDA site extent);
projwin is ULX ULY LRX LRY in metres (+proj=stere +lat_0=-90 +R=1737400).
Existing files are skipped (--force to redo); downloads resume.
lunar process¶
usage: lunar process [-h] [--from-file FILE] [--output-dir DIR] [--keep] [--force] [--workers N]
[--projection PROJ] [--resolution M] [--no-web] [--data-dir DIR]
[SOURCE ...]
positional arguments:
SOURCE Product IDs (e.g. M1096757719LE), local .IMG paths, or PDS URLs.
options:
-h, --help show this help message and exit
--from-file FILE Text file of sources, one per line (#comments ignored).
--output-dir DIR Output directory (default: current working directory).
--keep Keep the downloaded EDR and the intermediate ISIS cubes.
--force Redo steps whose output exists.
--workers N Parallel workers for batch processing (default: 1).
--projection PROJ ISIS map projection for mosrange (default: equirectangular).
--resolution M Map resolution in m/pixel.
--no-web Use local SPICE kernels in spiceinit instead of the USGS web service.
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar process M1096757719LE
lunar process M1096757719LE M1096757719RE --workers 2
lunar process --from-file ids.txt --output-dir ./output
lunar process /data/M1096757719LE.IMG --keep --resolution 1
lunar process https://pds.lroc.im-ldi.com/data/.../M1096757719LE.IMG
Everything is written to --output-dir: the GeoTIFF <id>.tif (map-projected I/F,
DEFLATE-compressed) plus intermediates (<id>.IMG, <id>.cal.echo.cub, <id>.map.cub),
which are removed after success unless --keep. Steps whose output exists are
skipped, so re-running resumes (use --force to redo them).
lunar kaguya¶
usage: lunar kaguya [-h] [--instrument {tc,mi}] [--from-file FILE] [--output-dir DIR]
[--bbox WEST SOUTH EAST NORTH | --point LAT LON] [--radius-km KM]
[--product-type PT] [--inc MIN MAX] [--emi MIN MAX] [--phase MIN MAX]
[--time START END] [--limit N] [--no-web] [--shape SHAPE] [--csm | --no-csm]
[--only-naif-spice | --no-only-naif-spice] [--mapproject] [--projection PROJ]
[--resolution M] [--keep] [--force] [--download-only] [--dry-run]
[--workers N]
[SOURCE ...]
positional arguments:
SOURCE TC / MI product IDs (e.g. TC1W2B0_01_02936N034E0938) or local .lbl files.
options:
-h, --help show this help message and exit
--instrument, -i {tc,mi}
Terrain Camera or Multiband Imager (default: from SOURCE, else tc).
--from-file FILE Text file of sources, one per line (#comments ignored).
--output-dir, -o DIR Output directory (default: current working directory).
ODE search (instead of / in addition to SOURCE):
--bbox WEST SOUTH EAST NORTH
Bounding box in degrees.
--point LAT LON Search around a point (use with --radius-km).
--radius-km KM Radius for --point (default: 1 km).
--product-type, -t PT
TC: stereo (TCWL2B, default) or mono (TCSL2B); MI: vis (VIS2B, default) or
nir (NIR2B).
--inc MIN MAX Incidence angle range.
--emi MIN MAX Emission angle range.
--phase MIN MAX Phase angle range.
--time START END Observation time range (UTC).
--limit N Maximum number of products from the search (default: 10).
ISIS import:
--no-web spiceinit with local kernels ($ISISDATA/kaguya) instead of the web
service.
--shape SHAPE spiceinit shape: system (LOLA DEM in $ISISDATA/base/dems, default) or
ellipsoid.
--csm, --no-csm Write a CSM camera (.json) with isd_generate (default: TC always, MI with
--no-web).
--only-naif-spice, --no-only-naif-spice
TC: pass --only_naif_spice to isd_generate (default: with --no-web; MI
always).
--mapproject Also cam2map and write <id>.tif.
--projection PROJ ISIS projection for --mapproject (default: equirectangular).
--resolution M Map resolution in m/pixel for --mapproject.
--keep Keep the PDS .img and the map-projected cube.
--force Redo steps whose output exists.
--download-only Download (and gunzip) only; no ISIS processing.
--dry-run Print the ISIS commands without downloading or running anything.
--workers N Products processed in parallel (default: 1).
Examples
--------
lunar kaguya TC1W2B0_01_02936N034E0938 TC2W2B0_01_02936N036E0938 -o ./tc
lunar kaguya --point 34.0 93.8 --radius-km 2 --limit 4 -o ./tc
lunar kaguya --bbox 93.5 33.9 94.0 34.1 --product-type mono --inc 40 70 -o ./tc
lunar kaguya ./tc/TC1W2B0_01_02936N034E0938.lbl --mapproject --resolution 10
lunar kaguya TC1W2B0_01_02936N034E0938 --download-only
lunar kaguya TC1W2B0_01_02936N034E0938 --dry-run
lunar kaguya MVA_2B2_01_01935N340E0939 MNA_2B2_01_01935N339E0939 -o ./mi
lunar kaguya --instrument mi --point 34.0 93.9 --product-type nir --limit 2 -o ./mi
Per product, <output-dir> gets <id>.lbl, <id>.cub (kaguyatc2isis / kaguyami2isis
+ spiceinit), <id>.json (CSM camera from isd_generate) and, with --mapproject,
<id>.tif. MI cubes hold all VIS (5) or NIR (4) bands; ALE's MI drivers need
local kernels, so MI CSM cameras default to --no-web runs only (--csm forces).
The instrument is inferred from the product IDs (MI: M[VN]A_2B2_...) unless
--instrument is given.
Steps whose output exists are skipped (use --force to redo them).
--bbox is WEST SOUTH EAST NORTH, longitudes positive east.
lunar shadowcam¶
usage: lunar shadowcam [-h] [--from-file FILE] [--output-dir DIR] [--product {raw,cal}]
[--bbox WEST SOUTH EAST NORTH | --point LAT LON | --aoi FILE_OR_WKT]
[--radius-km KM] [--inc MIN MAX] [--emi MIN MAX] [--phase MIN MAX]
[--time START END] [--limit N] [--web] [--shape SHAPE] [--no-csm]
[--validate] [--mapproject] [--dem DEM] [--resolution M] [--t-srs PROJ]
[--projection PROJ] [--keep] [--force] [--download-only] [--dry-run]
[--workers N]
[SOURCE ...]
positional arguments:
SOURCE Observation / product IDs (M013178466S, M013178466SE, M013178466SC) or
local .cub files.
options:
-h, --help show this help message and exit
--from-file FILE Text file of sources, one per line (#comments ignored).
--output-dir, -o DIR Output directory (default: current working directory).
--product, -t {raw,cal}
raw (M...SE, ASP's example, default) or cal (M...SC) for IDs and searches.
ODE search (instead of / in addition to SOURCE):
--bbox WEST SOUTH EAST NORTH
Bounding box in degrees.
--point LAT LON Search around a point (use with --radius-km).
--aoi FILE_OR_WKT Area of interest: GeoJSON / WKT file or WKT polygon string.
--radius-km KM Radius for --point (default: 1 km).
--inc MIN MAX Incidence angle range.
--emi MIN MAX Emission angle range.
--phase MIN MAX Phase angle range.
--time START END Observation time range (UTC).
--limit N Maximum number of products from the search (default: 10).
Processing:
--web spiceinit with the USGS SPICE web service (isd_generate still needs local
kernels).
--shape SHAPE spiceinit shape: system (LOLA DEM in $ISISDATA/base/dems, default) or
ellipsoid.
--no-csm Do not write a CSM camera (.json) with isd_generate.
--validate Compare ISIS and CSM cameras with cam_test (<id>.cam_test.txt).
--mapproject Also write a map-projected <id>.tif.
--dem DEM DEM for ASP mapproject (default: ISIS cam2map).
--resolution M Map resolution in m/pixel for --mapproject.
--t-srs PROJ PROJ string for ASP mapproject with --dem.
--projection PROJ ISIS projection for --mapproject without --dem (default: equirectangular).
--keep Keep the ISIS map-projected cube.
--force Redo processing steps whose output exists.
--download-only Download only; no processing.
--dry-run Print the ISIS / ASP commands without downloading or running anything.
--workers N Products processed in parallel (default: 1).
Examples
--------
lunar shadowcam M074289249S M074296291S -o ./sc
lunar shadowcam M013178466SC --validate -o ./sc
lunar shadowcam --point -89.67 129.8 --radius-km 5 --inc 80 90 --limit 4 -o ./sc
lunar shadowcam --aoi malapert.geojson --product cal --download-only -o ./sc
lunar shadowcam ./sc/M013178466SE.cub --mapproject --dem ref.tif --resolution 1.7
lunar shadowcam M013178466S --dry-run
Follows the ASP 3.7 ShadowCam example, which needs ASP's custom ISIS / ALE
build and the KPLO kernels in $ISISDATA/kplo/kernels (rsync.im-ldi.com::kplo).
Observation IDs (M...S) map to the raw cube M...SE (used in ASP's example) or,
with --product cal, the calibrated M...SC. Per product, <output-dir> gets
<id>.cub (spiceinit'ed in place), <id>.json (isd_generate), with --validate
<id>.cam_test.txt and with --mapproject <id>.tif (ASP mapproject with --dem,
else ISIS cam2map). Steps whose output exists are skipped (--force redoes them).
--bbox is WEST SOUTH EAST NORTH, longitudes positive east.
lunar stereo¶
usage: lunar stereo [-h] [--work-dir DIR] [--res M] [--dem TIF] [--image-res M] [--no-align]
[--max-displacement M] [--no-csm] [--local-spice] [--processes N]
[--threads N] [--stereo-opt KEY=VALUE] [--force] [--dry-run] [--data-dir DIR]
left right
positional arguments:
left Left image: NAC EDR product ID, .IMG or .cub path.
right Right image: NAC EDR product ID, .IMG or .cub path.
options:
-h, --help show this help message and exit
--work-dir DIR
--res M DEM m/px (default: 2).
--dem TIF Prior DEM to mapproject onto and align to.
--image-res M Mapprojected image m/px when --dem is set (default: 1).
--no-align Skip pc_align to --dem.
--max-displacement M
--no-csm Use ISIS cameras instead of CSM.
--local-spice
--processes N
--threads N
--stereo-opt KEY=VALUE
Extra / overriding parallel_stereo option (repeatable).
--force
--dry-run Print the commands without running them.
--data-dir DIR
Examples
--------
lunar stereo M181058717LE M181073012LE --res 2 --work-dir pair1
lunar stereo L.IMG R.IMG --dem ldem.tif --res 2 # mapproject first, align to the DEM
lunar stereo L.cub R.cub --dry-run
Needs ISIS and ASP on PATH (or ASP_ROOT / ISISROOT).
lunar sfs¶
usage: lunar sfs [-h] [--config YAML] [--dump-config] [--check] [--from-file FILE] [--dem TIF]
[--region REGION] [--crop-km KM] [--aoi FILE_OR_WKT | --projwin ULX ULY LRX LRY]
[--work-dir DIR] [--res M] [--preset {bertone,asp}] [--ba-res M]
[--reduce N|auto|none] [--no-csm] [--local-spice]
[--registration {stereo,residuals,none}] [--stereo-pairs N]
[--max-displacement M] [--no-refine] [--max-offset-p85 M]
[--selection {coverage,kmedoids,image_subset,all}] [--selection-clusters N]
[--sfs-cameras {csm,isis}] [--cameras-from {ba,published}] [--max-sfs-images N]
[--max-slew DEG] [--max-sfs-slew DEG] [--max-images N] [--max-pixel-scale M]
[--ensemble N] [--seed N] [--region-id ID] [--processes N] [--threads N]
[--ba-opt KEY=VALUE] [--refine-opt KEY=VALUE] [--sfs-opt KEY=VALUE] [--force]
[--dry-run] [--data-dir DIR]
[SOURCE ...]
positional arguments:
SOURCE NAC EDR product IDs (downloaded), .IMG or calibrated .cub paths (default
with --aoi / --region: search the local EDR index).
options:
-h, --help show this help message and exit
--config YAML Run configuration file (flags override it).
--dump-config Print the effective configuration as YAML and exit.
--check Compare tool versions, settings and input files with
WORK_DIR/provenance.json and exit (status 1 when they differ).
--from-file FILE Text file of sources, one per line.
--dem TIF Prior DEM (e.g. LOLA LDEM GeoTIFF), or pgda (default with --region).
--region REGION Artemis III region (id, name or PGDA site, see lunar reference list): sets
the crop, product prefix and image search, and the PGDA LOLA 5 m prior
DEM.
--crop-km KM Square crop of this side at the region centre.
--aoi FILE_OR_WKT Area of interest (GeoJSON / WKT file or WKT, lon/lat): crops a polar
stereographic prior DEM and, without SOURCEs, selects the images.
--projwin ULX ULY LRX LRY
Crop window in the prior DEM's projected units.
--work-dir DIR Working / output directory (default: sfs_work).
--res M SfS DEM m/px (default: 5).
--preset {bertone,asp}
Option defaults (default: bertone).
--ba-res M m/px of the images mapprojected for bundle adjustment (default: 1, NAC
native).
--reduce N|auto|none ISIS reduce factor of the SfS cubes (default: auto = target / native
m/px).
--no-csm Use ISIS cameras instead of CSM.
--local-spice spiceinit with local kernels instead of the SPICE web service.
--registration {stereo,residuals,none}
Register cameras to the prior DEM from stereo DEMs, BA points or not at
all (default: stereo).
--stereo-pairs N Max stereo pairs (default: 30).
--max-displacement M pc_align --max-displacement for registration (default: 400).
--no-refine Skip the --heights-from-dem refinement.
--max-offset-p85 M Drop images whose 85th-percentile mapprojected match offset exceeds this
(default: 1.8).
--selection {coverage,kmedoids,image_subset,all}
SfS image selection (default: coverage = 3 Sun directions 30 deg apart per
pixel; kmedoids = Bertone et al. k-medoids seeding + coverage refinement).
--selection-clusters N
Medoids for --selection kmedoids (default: 30).
--sfs-cameras {csm,isis}
Cameras of the reduced SfS cubes: re-mapped CSM (default) or ISIS
approximate models.
--cameras-from {ba,published}
ba (default) or published: Bertone et al. adjusted cameras, skipping
bundle adjustment.
--max-sfs-images N Cap on SfS images.
--max-slew DEG Search cut on |slew| (default: none; see --max-sfs-slew).
--max-sfs-slew DEG Only images with |slew| below this go into SfS (default: 5; slewed images
still help BA / stereo).
--max-images N Cap on searched images before download: stereo pairs + illumination
coverage (default: none).
--max-pixel-scale M Search cut on the image m/px (default: 1.5).
--ensemble N SfS ensemble members (default: 0).
--seed N Random seed of the ensemble subsets (default: 0).
--region-id ID Product name prefix (default: region or work dir name).
--processes N
--threads N
--ba-opt KEY=VALUE Extra / overriding bundle_adjust option (repeatable; VALUE none drops it).
--refine-opt KEY=VALUE
Extra / overriding refinement bundle_adjust option (repeatable; VALUE none
drops it).
--sfs-opt KEY=VALUE Extra / overriding parallel_sfs option (repeatable; VALUE none drops it).
--force Recompute steps whose outputs exist.
--dry-run Print the commands without running them.
--data-dir DIR Override Parquet data directory.
Examples
--------
lunar sfs --config examples/malapert_crop.yaml
lunar sfs --config run.yaml --res 2 --sfs-opt smoothness_weight=0.05 # flags override the file
lunar sfs --config run.yaml --dump-config > effective.yaml # print every setting
lunar sfs --config run.yaml --check # compare tools / config / inputs with the work dir
lunar sfs --region malapert --crop-km 2.5 --work-dir malapert_crop # PGDA prior DEM, ROI search
lunar sfs --aoi site.geojson --dem LDEM_87S_5MPP_ADJ.TIF --work-dir malapert
lunar sfs M1234567890LE M1234567891RE ... --dem LDEM_87S_5MPP_ADJ.TIF \
--projwin -10000 50000 0 40000 --res 5 --work-dir malapert
lunar sfs raw/*.IMG --dem ldem.tif --registration residuals --processes 8
lunar sfs --aoi "POLYGON((...))" --dem ldem.tif --dry-run # print the commands only
Config files are flat YAML mappings of the same settings (keys as printed by
--dump-config); command-line flags override them. Each run writes the effective
settings to WORK_DIR/config.yaml and appends its environment, tool versions,
input checksums and per-step commands to WORK_DIR/provenance.json.
Steps (Bertone et al. 2026, PSJ 7:118): [search + slew/resolution cut + download] ->
calibrate + CSM cameras -> crop/resample prior DEM -> sort by Sun azimuth -> mapproject at
--ba-res -> bundle adjust -> drop badly registered images -> register to the prior DEM
(stereo DEMs or BA points, translation only) -> refine with --heights-from-dem -> drop
again -> mapproject at --res -> max-lit QA mosaics (all + 30 deg Sun bins) -> select images ->
reduce cubes to --res -> parallel_sfs -> products.
Re-running resumes: steps whose outputs exist are skipped (--force to redo).
Needs ISIS and ASP on PATH (or ASP_ROOT / ISISROOT).
lunar sfs-report¶
usage: lunar sfs-report [-h] [-o DIR] [--sfs-dem TIF] [--prior-dem TIF] [--region-id ID] [--res M]
[--ldec TIF] [--toterr TIF] [--slperr TIF] [--ldem-slope TIF]
[--lola-points CSV] [--lola-xyzi XYZI] [--published-dem TIF]
[--region REGION] [--pgda KIND [KIND ...]] [--fetch-published]
[--reference-dir DIR] [--sections NAME [NAME ...]] [--preview-size PX]
WORK_DIR
positional arguments:
WORK_DIR lunar sfs work directory.
options:
-h, --help show this help message and exit
-o, --output-dir DIR Destination (default: WORK_DIR/report).
--sfs-dem TIF SfS DEM (default: products GLDELEV or sfs/).
--prior-dem TIF Prior DEM (default: dem/prior-<RES>m.tif).
--region-id ID Product name prefix (default: from config.yaml).
--res M Product resolution label (default: from config.yaml).
--ldec TIF PGDA LOLA count raster (*_ldec.tif).
--toterr TIF PGDA elevation uncertainty (*_toterr.tif).
--slperr TIF PGDA slope uncertainty (*_slperr.tif).
--ldem-slope TIF PGDA LDEM slope (*_slp.tif).
--lola-points CSV LOLA points as an ASP CSV (easting, northing, height).
--lola-xyzi XYZI PGDA LOLA point cloud (*.xyzi).
--published-dem TIF Published Bertone et al. SDEM (GLDELEV).
--region REGION Artemis III region: download its PGDA files (see --pgda) for the inputs
not given.
--pgda KIND [KIND ...]
PGDA files fetched with --region (default: ldec toterr slp slperr xyzi).
--fetch-published With --region: extract the published GLDELEV from the Zenodo zip (HTTP
range reads).
--reference-dir DIR Download directory for --region files (default: the reference cache).
--sections NAME [NAME ...]
Only these sections (default: all).
--preview-size PX Longer side of the map figures (default: 800).
Examples
--------
lunar sfs-report malapert_crop # work dir files only
lunar sfs-report malapert_crop --region malapert # + PGDA LDEC, uncertainty maps, LOLA points
lunar sfs-report malapert_crop --region malapert --fetch-published # + published SDEM
lunar sfs-report w --toterr Site23_final_adj_5mpp_toterr.tif --lola-points lola.csv -o w/report2
Sections (skipped when their inputs are missing): bundle-adjustment residuals before /
after and match offsets (Fig. 5); removed images; illumination coverage with 0/1/2/>=3
non-redundant Sun directions (Figs. 3, 6); SfS minus prior DEM, split by LOLA count
(Table 2); SfS minus LOLA points vs slope (Fig. 7); ensemble uncertainty (Fig. 8);
SfS - LDEM residuals over the LDEM uncertainty maps (Fig. 9); SfS minus the published SDEM.
Writes OUTPUT_DIR/report.html (figures embedded), metrics.json, tables/*.csv, figures/*.png.
lunar workspace¶
usage: lunar workspace [-h] [--sql SQL] [--tables] [--export TABLE PATH] [--csv FILE]
[--max-rows N] [--memory-limit SIZE] [--threads N]
WORK_DIR
positional arguments:
WORK_DIR Work directory or .duckdb file.
options:
-h, --help show this help message and exit
--sql SQL Run SQL and print the result (repeatable).
--tables List tables and views with row counts.
--export TABLE PATH Write a table or view to Parquet / CSV.
--csv FILE Write the last --sql result to CSV.
--max-rows N Rows to print (default: 50).
--memory-limit SIZE DuckDB memory_limit (default: 1GB).
--threads N DuckDB threads (default: all cores).
Examples
--------
lunar workspace work/malapert # tables and views with row counts
lunar workspace work/malapert --sql "SELECT * FROM ba_run_summary"
lunar workspace work/malapert --sql "SELECT run, rule, count(*) FROM image_rejections GROUP BY ALL"
lunar workspace work/malapert --sql "SELECT * FROM image_rejections_at(1.5, 0.8, 1.0, 1)"
lunar workspace work/malapert --export ba_image_stats ba_stats.parquet
WORK_DIR is a lunar sfs work directory (its lunar.duckdb) or a .duckdb file; it is
opened read-only. Tables: images, pairs, ba_runs, ba_residual_stats,
ba_pixel_residuals, ba_match_offsets, ba_points, ba_convergence, ba_camera_offsets,
rejection_params. Views: ba_image_stats, ba_run_summary, image_rejections.
--export writes Parquet for .parquet paths, else CSV (geometries as WKT).
lunar serve¶
usage: lunar serve [-h] [--port PORT] [--host HOST] [--data-dir DIR] [--images DIR]
[--runs-dir DIR] [--admin-token TOKEN] [--no-browser]
options:
-h, --help show this help message and exit
--port PORT Port to listen on (default: 8080).
--host HOST Address to bind (default: localhost); 0.0.0.0 serves the network (read-only
there).
--data-dir DIR Directory containing parquet files. Defaults to LUNAR_DATA_DIR or the user
data dir.
--images DIR Also serve the GeoTIFF / PNG / JPEG files under DIR (with Range) for the
Image view.
--runs-dir DIR SfS runs listed in the Settings panel (default: LUNAR_RUNS_DIR).
--admin-token TOKEN Let remote clients with this token (Authorization: Bearer TOKEN or
?token=TOKEN) start jobs and see local paths; 'auto' generates one.
--no-browser Don't open a browser tab automatically.
Examples
--------
lunar serve
lunar serve --port 9000
lunar serve --data-dir /mnt/lroc-data
lunar serve --images ~/sfs_runs # browse local GeoTIFF / COG results in the Image view
lunar serve --host 0.0.0.0 # share on the network; remote clients are read-only
lunar serve --host 0.0.0.0 --admin-token auto # ... and print a token for remote admin
Admin (the Settings panel: build indexes, download, see local paths) is allowed from this
machine (loopback) and for requests carrying --admin-token; everyone else can browse,
search and view. Use `lunar app` for a desktop window.
lunar app¶
usage: lunar app [-h] [--port PORT] [--host HOST] [--data-dir DIR] [--images DIR] [--runs-dir DIR]
[--admin-token TOKEN] [--backend {auto,webview,chromium,browser}]
options:
-h, --help show this help message and exit
--port PORT Port to listen on (default: any free).
--host HOST Address to bind (default: 127.0.0.1); 0.0.0.0 serves the network (read-
only there).
--data-dir DIR Directory containing parquet files. Defaults to LUNAR_DATA_DIR or the user
data dir.
--images DIR Also serve the GeoTIFF / PNG / JPEG files under DIR (with Range) for the
Image view.
--runs-dir DIR SfS runs listed in the Settings panel (default: LUNAR_RUNS_DIR).
--admin-token TOKEN Let remote clients with this token (Authorization: Bearer TOKEN or
?token=TOKEN) start jobs and see local paths; 'auto' generates one.
--backend {auto,webview,chromium,browser}
Window backend (default: auto, in the order above).
Examples
--------
lunar app
lunar app --images ~/lunar_runs
lunar app --host 0.0.0.0 --port 8080 # window here, read-only page for the network
lunar app --backend browser # a normal browser tab instead
The server runs on this machine (a free port on 127.0.0.1 by default) and stops when
the window closes. Window backends, first available wins (--backend auto):
webview pywebview: Qt WebEngine on Linux (pip install "lunar-toolkit[app]",
or PyGObject + WebKitGTK), Edge WebView2 on Windows, WebKit on macOS
chromium Chrome / Chromium / Edge / Brave in --app mode (own profile in the cache dir)
browser the default browser (Ctrl-C stops the server)