ExoJAX Utility Functions for Spectral Modeling: A Complete Guide
ExoJAX ships a lightweight exojax.utils package that provides essential helper functions for constructing spectral grids, converting photometric magnitudes, analyzing opacity profiles, and validating array data in radiative transfer workflows.
The exojax.utils module in the hajimekawahara/exojax repository consolidates pure NumPy/JAX tools needed throughout the opacity and radiative-transfer pipelines. These utilities handle the "bookkeeping" of spectral modeling—from wavenumber grid generation to filter curve downloads—without pulling in heavy computational solvers, making them ideal for forward modeling, retrieval algorithms, and post-processing scripts.
Spectral Grid and Wavelength Handling
The grid utilities form the foundation of most ExoJAX workflows. Located in src/exojax/utils/grids.py and src/exojax/utils/spectral_bands.py, these functions generate evenly spaced wavenumber arrays, handle unit conversions, and validate grid properties.
Key functions include:
wavenumber_grid– Constructs log-spaced (ESLOG) or linear wavenumber grids with automatic resolution calculationextended_wavenumber_grid– Generates extended grids for convolution paddingnu2wavandwav2nu– Convert between wavenumber (cm⁻¹) and wavelength (µm)velocity_gridanddelta_velocity_from_resolution– Build velocity grids for rigid-rotation convolutiongrid_resolution– Estimates the spectral resolving power $R$check_eslog_wavenumber_grid– Validates that a grid follows the expected evenly-spaced-log patternspectral_band_edgesandspectral_bands– Generate band centers and edges for correlated-k distribution calculations
from exojax.utils.grids import wavenumber_grid
# Build a high-resolution grid from 1.0–2.5 µm (converted to cm⁻¹)
x0_cm = 1.0e4 / 2.5 # ν_max (cm⁻¹)
x1_cm = 1.0e4 / 1.0 # ν_min (cm⁻¹)
nu_grid, wav_grid, R = wavenumber_grid(
x0_cm, x1_cm, N=4000,
xsmode='premodit',
wavelength_order='descending',
unit='cm-1'
)
print(f"Resolution ≈ {R:.0f}, ν‑grid shape: {nu_grid.shape}")
Photometry and Filter Utilities
For comparing synthetic spectra against observed photometry, src/exojax/utils/photometry.py provides SVO filter service integration and magnitude calculations.
Core capabilities include:
download_filter_from_svo– Downloads filter transmission curves from the Spanish Virtual Observatorydownload_zero_magnitude_flux_from_svo– Retrieves zero-point fluxes for magnitude calibrationapparent_magnitude– Converts a model spectrum to apparent magnitude through a given filterapparent_magnitude_isothermal_sphere– Specialized version for isothermal sphere geometryaverage_resolution– Computes the filter-averaged spectral resolution
import jax.numpy as jnp
from exojax.utils.photometry import (
download_filter_from_svo,
download_zero_magnitude_flux_from_svo,
apparent_magnitude,
)
# Load 2MASS Ks filter from SVO
flt_id = "2MASS/2MASS.Ks"
nu_filt, tr_filt = download_filter_from_svo(flt_id)
# Get zero-point flux in consistent units
nu0, f0_nu = download_zero_magnitude_flux_from_svo(flt_id, unit="cm-1")
# Convert model flux (erg s⁻¹ cm⁻² (cm⁻¹)⁻¹) to magnitude
mag = apparent_magnitude(model_flux, nu_filt, tr_filt, f0_nu)
print(f"{flt_id} apparent magnitude = {mag:.3f}")
Opacity Diagnostics and Pressure Extraction
The src/exojax/utils/opautils.py module contains specialized tools for optical depth analysis. The primary function, pressure_at_given_opacity, extracts the pressure level where a specific optical depth (e.g., $\tau = 1$) is reached for each wavelength—critical for identifying photosphere depths.
import numpy as np
from exojax.utils.opautils import pressure_at_given_opacity
# dtau: differential optical depth per layer (N_layer × N_λ)
# Parr: pressure array in bar (ascending order)
Parr = np.logspace(-6, 2, dtau.shape[0])
# Find τ=1 pressure for each wavelength
p_tau1 = pressure_at_given_opacity(dtau, Parr, tauextracted=1.0)
# Locate photosphere at specific wavenumber
idx = np.argmin(np.abs(nu_grid - 1500.0))
print(f"τ=1 pressure at 1500 cm⁻¹ ≈ {p_tau1[idx]:.2e} bar")
Interpolation and Array Validation
For data preprocessing and safety checks, ExoJAX provides robust interpolation and validation helpers:
interp2d_bilinear(src/exojax/utils/interp.py) – Performs bilinear interpolation on arbitrary 2-D grids using JAX-compatible operationsis_sorted(src/exojax/utils/checkarray.py) – Detects whether an array is in ascending or descending orderis_outside_range– Tests if values lie outside specified bounds, useful for input validation
These functions include safeguards against common array handling errors that could propagate through radiative transfer calculations.
Supporting Utilities and Constants
Several additional modules provide infrastructure and reference data:
progbar(src/exojax/utils/progbar.py) – Lightweight text-based progress indicator for long-running loops- URL constants (
src/exojax/utils/url.py) – Centralized endpoints for external databases includingurl_svo_filter,url_ExoMol,url_HITEMP, andurl_HITRAN - Physical constants (
src/exojax/utils/constants.py) – Atomic masses, planetary radii, and unit conversion factors jaxstatus(src/exojax/utils/jaxstatus.py) – Exposes JAX configuration flags (x64 mode, platform detection) for debugging
Summary
The exojax.utils package provides a comprehensive toolkit for spectral modeling workflows:
- Grid construction via
wavenumber_gridand conversion utilities ingrids.py - Photometric calibration with SVO filter downloads and magnitude calculations in
photometry.py - Opacity analysis through
pressure_at_given_opacityinopautils.py - Data validation using
is_sortedand interpolation helpers - Infrastructure support including progress bars, URL constants, and JAX status checks
These functions are deliberately lightweight, well-tested (see tests/unittests/utils), and JAX-compatible, ensuring they integrate seamlessly into both research scripts and production retrieval pipelines.
Frequently Asked Questions
How do I create a wavenumber grid compatible with ExoJAX's opacity calculators?
Use wavenumber_grid from src/exojax/utils/grids.py. Specify the spectral range in cm⁻¹, the number of points, and the cross-section mode (e.g., xsmode='premodit'). The function returns the wavenumber grid, wavelength grid, and estimated resolving power $R$, automatically handling the log-spacing required for high-resolution spectroscopy.
Can ExoJAX convert synthetic spectra to photometric magnitudes for comparison with observations?
Yes. The src/exojax/utils/photometry.py module provides download_filter_from_svo to retrieve transmission curves from the SVO Filter Profile Service, download_zero_magnitude_flux_from_svo for calibration, and apparent_magnitude to integrate your model spectrum through the filter. These handle the proper normalization and unit conversions required for accurate magnitude calculations.
How do I determine the atmospheric pressure level corresponding to the observed photosphere?
Use pressure_at_given_opacity in src/exojax/utils/opautils.py. Pass the differential optical depth array (dtau) and pressure array (Parr), specifying the target optical depth (default $\tau = 1$). The function returns an array of pressure values representing the $\tau = 1$ surface for each wavelength, which defines the photosphere depth in transmission or emission spectra.
Are these utility functions dependent on JAX, or can they be used with standard NumPy?
Most utilities are JAX-agnostic and work with standard NumPy arrays, though they return JAX-compatible arrays when JAX is available. Functions like wavenumber_grid and pressure_at_given_opacity use pure NumPy operations by default, while interp2d_bilinear is specifically designed for JAX's functional programming patterns. The jaxstatus utility helps verify your JAX configuration when needed.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →