chore: version packages#10
Merged
Merged
Conversation
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This PR was opened by the Changesets release GitHub action. When you're ready to do a release, you can merge this and the packages will be published to npm automatically. If you're not ready to do a release yet, that's fine, whenever you add more changesets to main, this PR will be updated.
Releases
@walkthru-earth/objex@1.3.0
Minor Changes
07e1570Thanks @yharby! - Canonical connection identity and deduplication across every write path.utils/connection-identity.ts(exported fromsrc/lib/index.ts):connectionIdentityKey,isSameConnectionIdentity,normalizeEndpoint,normalizeProvider,ConnectionIdentityInput. Identity is provider-aware:azure→provider|endpoint|bucket,gcs→provider|bucket(global namespace),s3with empty endpoint →s3|bucket|region(region is load-bearing for signing), all other S3-compatible providers →provider|normalizedEndpoint|bucket.normalizeEndpointlowercases host, strips default ports (:443/:80) and trailing slashes, and preserves explicit non-default ports and pathnames sohttpvshttps,:443vs empty, and trailing-slash drift collapse to one key.connectionsstore: removedfindByBucketEndpoint(bucket+endpoint string match, which produced silent duplicates for AWS same-bucket-different-region and custom S3-compat scheme/port drift, and was bypassed entirely by the manual Add Connection dialog). Every write path now dedups throughconnectionIdentityKey:save(config)returns{ id, existed }. Onexisted: true, the row is reused and credentials from the new config overwrite the old ones.update(id, config)throws the newDuplicateConnectionErrorwhen the new identity would collide with a different saved row, so edits can't silently produce phantom duplicates.saveHostConnection(detected)continues to be the auto-detect entry and returns the final id, either reused or newly inserted.findByIdentity(input)exposes the same key for callers that need to check without writing.ConnectionDialogsurfaces both outcomes: amber "merged into existing" notice on dedup and destructive "already used by X" block on edit collision, with the offending connection's name.$lib/leaks indist/.676c792Thanks @yharby! - Bump the@developmentseed/deck.gl-geotifffamily to0.6.0-alpha.1and add two new viewers plus a dual-path Zarr renderer. No breaking changes to existing tabs, and CogViewer behavior is unchanged.What's new
StacTabViewer).ViewerRouternow detects STAC Items / FeatureCollections / Collections / Catalogs via a 256 KB adapter peek (utils/stac.ts::classifyStac) and mounts a tab wrapper withMap/STAC Browser/JSONbuttons (URL hash#map/#stac-browser/#code, shareable). The user can always toggle back to the third-party stac-browser iframe. For Collection / Catalog inputs,utils/stac-hydrate.ts::hydrateStacItemswalkslinks[rel=item|child|next]with a 12-way concurrency pool and a 2000-item cap, emitting progressive batches so the MosaicLayer starts rendering after ~1–2s. Each inner COG still runs throughselectCogPipeline, so palette-indexed short-circuits, non-uint custom pipelines, LinearRescale, andnormalizeCogGeotiff(overview strip + polar bbox clamp) all apply per scene. SharedDecoderPoolandcreateEpsgResolveracross every inner source.eo:bands.common_nameor MPC/Element 84/AWS asset-key heuristics identify at least the red/green/blue Sentinel-2 bands. Preset dropdown (True Color / False-Color IR / SWIR / Vegetation / Agriculture) drives the v0.6MultiCOGLayer.compositeprop, and aFilterNoDataVal+LinearRescalepipeline (0..0.3 default for L2A reflectance) mask scene edges and stretch contrast.utils/zarr.ts::detectGeoZarrinspects hierarchy attributes for the GeoZarr convention (multiscales+ spatial + CRS). Matching stores render via@developmentseed/deck.gl-zarrZarrLayeronMapboxOverlay; anything else falls through to the existing@carbonplan/zarr-layerpath with its 10 k-tile guard and numcodecs codec aliases.utils/stac.ts(STAC item/FeatureCollection shape checks, Sentinel band extraction, bbox helper).utils/cog.tsgainsbuildMosaicSourceMeta,buildBandRenderPipeline(composesFilterNoDataVal+LinearRescalein GPU-correct order).utils/zarr.tsgainsdetectGeoZarrandzarrTileToImageData.modeprop. Accepts'single'(default, full band + color-ramp UI) or'multi'(rescale slider only). MultiCogViewer uses the new mode; existing CogViewer is unchanged.Package bumps
@developmentseed/deck.gl-geotiff,deck.gl-raster,geotiff,proj,epsg:^0.5.0 → ^0.6.0-alpha.1. New deps:@developmentseed/deck.gl-zarr@^0.6.0-alpha.1(pulls in@developmentseed/geozarrtransitively).zarritabumped^0.6.2 → ^0.7.1, forced across the tree viapnpm.overridesso@carbonplan/zarr-layer@^0.4.3runs on the same major.Patches
patches/@developmentseed__deck.gl-geotiff@0.5.0.patchrenamed and re-attached as@0.6.0-alpha.1.patch. Both hunks (proj4+overantimeridian fix,inferRenderPipelinere-export) still apply unchanged, upstream tickets #366 and PR #374 remain open.New patch
patches/@carbonplan__zarr-layer@0.4.3.patchreplaces two calls tozarr.tryWithConsolidated()withPromise.resolve(baseStore). The helper was removed in zarrita 0.7, and the override above forces 0.7 across the tree, which otherwise surfaced as a runtime(void 0) is not a functioninside_onAddAsyncwhen mounting the legacy ZarrLayer. Consolidated metadata (.zmetadata) is still fetched manually by the library's own_loadV2, so skipping the helper is behavior-preserving.Vite config
optimizeDeps.includeextended with@developmentseed/deck.gl-zarrand itsgeozarr+raster-reprojectleaves, pluszarritaitself.4cf01c5Thanks @yharby! - GPU colormap sprite, histogram slider, and 4-band COG fix.GPU
Colormapsprite with 107 rampsSingle-band COGs and mosaics now render through the v0.6
Colormapshader module sampling@developmentseed/deck.gl-raster/gpu-modules/colormaps.png(256x107 RGBA, matplotlib + rio-tiler + cmocean). Switching ramps is a uniform update oncolormapIndex, no tile re-decode. The CPU baker normalizes band N intocolor.rwithr = 1 + round(t * 254)and reservesr = 0as a nodata sentinel soFilterNoDataVal({ value: 0 })discards those fragments before the ramp sample.New helper module
utils/colormap-sprite.tsdecodes the sprite once per session and caches the uploadedsampler2DArraytexture per luma.glDevicevia aWeakMap. ExportsCOLORMAP_INDEX(all 107 names),COLORMAP_NAMES(sorted),loadColormapSprite(),getColormapTexture(device), andspriteBackgroundStyle(name, heightPx)for CSS previews.CogControls.sveltepreviews every ramp by slicing the sprite as a CSS background-image. Curated 10-ramp "pinned" grid (gray, terrain, viridis, magma, turbo, spectral, inferno, plasma, cividis, rdylgn), plus a search field and a scrollable full list of all 107.Histogram behind the rescale slider
selectCogPipelinenow accepts anonHistogram?: (bins: Uint32Array) => voidcallback. The CPU baker emits a 64-bin histogram (HISTOGRAM_BIN_COUNT) built over the tile's valid samples, stored inCogViewer/StacMosaicVieweras$state.raw<Uint32Array>and rendered byCogControlsas an SVG bar chart behind the rescale sliders. The active[min, max]window draws as a translucent band so the slider visualizes what it is actually clipping.rescaleApplicablenow returnstruewhenbandConfig.mode === 'single'in addition to the legacy uint-RGB case. The single-band path builds its pipeline as[Sampler2DArrayPrecision, FilterNoDataVal, LinearRescale?, Colormap], so the slider stretchescolor.rbefore the ramp lookup.NAIP 4-band opacity fix + dynamic band detection
needsCustomPipelineForConfignow forces the CPU path forgeotiff.count === 4in RGB mode, so the 4th NAIP band is no longer silently interpreted as alpha by the library-default RGBA pipeline.StacMosaicViewerdetects band count +SampleFormatdynamically on the first COG thatMosaicLayer.getSourceresolves (viageotiff.countandcachedTags.sampleFormat), reseedsbandConfigviadefaultBandConfig(count, sf), and updates<CogControls bandCount=...>so 4-band imagery exposes all four bands in the picker. Previously the mosaic hard-coded 3 bands.Sampler2DArrayPrecisionshim@developmentseed/deck.gl-raster@0.6.0-alpha.1'sColormapmodule injectsuniform sampler2DArray colormapTexture;without a precision qualifier, which the Apple-GPU path of luma.gl's WebGL2 backend rejects withERROR: 'sampler2DArray' : No precision specified. Local shimSampler2DArrayPrecision(inutils/cog.ts) injectsprecision highp sampler2DArray;atfs:#decland is chained immediately beforeColormapinbuildCustomRenderTile. Remove once upstream fixes.Dead code removed
Retired
COLOR_RAMP_STOPS,ColorRampId,interpolateRamp,rampToGradientCss, andcustomRenderTilefromutils/cog.ts. All superseded by the sprite path.ColorRampIdis now a type alias forColormapName(all 107 entries).objex-utilsBump coordinated with the main package via the
fixedchangeset config. No new re-exports,colormap-sprite.tsis not published because it depends on luma.glDevice/ WebGL2. Consumers who want GPU colormap rendering should depend on the full@walkthru-earth/objexpackage.439dfd7Thanks @yharby! - Add stac-geoparquet support.objex-utils: newstac-geoparquetmodule with pure transforms that any consumer can use:isStacGeoparquetSchema,stacRowToItem,flattenStacBbox,resolveStacAssetHref,pickStacPrimaryAsset, plusStacGeoparquetRow/StacBboxStruct/StacGeoparquetSchemaColumn/StacRowToItemOptionstypes.objexSvelte lib:ViewerRouterdetects stac-geoparquet via hyparquet schema sniff and routes matching.parquet/.geoparquetfiles toStacTabViewer. A newquery/stac-geoparquet.tshelper uses the existing DuckDB engine (presigned URL, single worker, cancellable) to materialize a STAC FeatureCollection in one shot;StacMosaicViewerconsumes it through the samebuildMosaicSourceMeta+ MosaicLayer path as JSON catalogs.StacTabViewernow shows a "Parquet" badge, relabels the last tab as "Table" (mountingTableViewer), and disables theSTAC Browseriframe button with a tooltip since Radiant Earth stac-browser is JSON-only. Thestac-mapDevSeed iframe handles parquet on its own, so its button is unchanged.4cf01c5Thanks @yharby! - STAC mosaic pixel inspection and stricter STAC JSON routing.Mosaic pixel inspection + info panel
StacMosaicViewernow exposes the sameInfobutton and pixel-inspection overlay thatCogViewerhas. Clicking a pixel inside a STAC Catalog / Collection / ItemCollection / stac-geoparquet tab surfaces the sampled band values plus the matching source id, and the info panel lists source count, detected band count, data type (captured asbuildDataTypeLabel(sampleFormat, bitsPerSample)on the first resolved COG), and union bounds.A
geotiffCache: Map<string, Promise<GeoTIFF>>is populated insidegetSourceand reused both forMosaicLayerrebuilds and for the map-click handler, so clicks do not trigger a second HTTP fetch. The click handler reverse-iteratesitemsRefto match mosaic z-order, finds the topmost source whose bbox contains the click, and callsreadPixelAtLngLat(...)against that source's cachedGeoTIFF.New translations
stac.mosaicInfoandstac.mosaicSourcesLabelfor English and Arabic.Stop routing plain JSON through StacTabViewer
ViewerRouter::detectStacnow propagatesclassifyStac(parsed)'s{ kind: 'none' }result in both the 256 KB peek branch and the full-read fallback. Previously any JSON that parsed returned{ kind: 'stac', classified: { kind: 'none' } }, which still mountedStacTabViewerand exposed thestac-mapandSTAC Browserbuttons on files that were not STAC at all (including GeoJSON FeatureCollections that fail the STAC shape checks). Plain JSON now falls through toCodeVieweras intended.@walkthru-earth/objex-utils@1.3.0
Minor Changes
676c792Thanks @yharby! - Bump the@developmentseed/deck.gl-geotifffamily to0.6.0-alpha.1and add two new viewers plus a dual-path Zarr renderer. No breaking changes to existing tabs, and CogViewer behavior is unchanged.What's new
StacTabViewer).ViewerRouternow detects STAC Items / FeatureCollections / Collections / Catalogs via a 256 KB adapter peek (utils/stac.ts::classifyStac) and mounts a tab wrapper withMap/STAC Browser/JSONbuttons (URL hash#map/#stac-browser/#code, shareable). The user can always toggle back to the third-party stac-browser iframe. For Collection / Catalog inputs,utils/stac-hydrate.ts::hydrateStacItemswalkslinks[rel=item|child|next]with a 12-way concurrency pool and a 2000-item cap, emitting progressive batches so the MosaicLayer starts rendering after ~1–2s. Each inner COG still runs throughselectCogPipeline, so palette-indexed short-circuits, non-uint custom pipelines, LinearRescale, andnormalizeCogGeotiff(overview strip + polar bbox clamp) all apply per scene. SharedDecoderPoolandcreateEpsgResolveracross every inner source.eo:bands.common_nameor MPC/Element 84/AWS asset-key heuristics identify at least the red/green/blue Sentinel-2 bands. Preset dropdown (True Color / False-Color IR / SWIR / Vegetation / Agriculture) drives the v0.6MultiCOGLayer.compositeprop, and aFilterNoDataVal+LinearRescalepipeline (0..0.3 default for L2A reflectance) mask scene edges and stretch contrast.utils/zarr.ts::detectGeoZarrinspects hierarchy attributes for the GeoZarr convention (multiscales+ spatial + CRS). Matching stores render via@developmentseed/deck.gl-zarrZarrLayeronMapboxOverlay; anything else falls through to the existing@carbonplan/zarr-layerpath with its 10 k-tile guard and numcodecs codec aliases.utils/stac.ts(STAC item/FeatureCollection shape checks, Sentinel band extraction, bbox helper).utils/cog.tsgainsbuildMosaicSourceMeta,buildBandRenderPipeline(composesFilterNoDataVal+LinearRescalein GPU-correct order).utils/zarr.tsgainsdetectGeoZarrandzarrTileToImageData.modeprop. Accepts'single'(default, full band + color-ramp UI) or'multi'(rescale slider only). MultiCogViewer uses the new mode; existing CogViewer is unchanged.Package bumps
@developmentseed/deck.gl-geotiff,deck.gl-raster,geotiff,proj,epsg:^0.5.0 → ^0.6.0-alpha.1. New deps:@developmentseed/deck.gl-zarr@^0.6.0-alpha.1(pulls in@developmentseed/geozarrtransitively).zarritabumped^0.6.2 → ^0.7.1, forced across the tree viapnpm.overridesso@carbonplan/zarr-layer@^0.4.3runs on the same major.Patches
patches/@developmentseed__deck.gl-geotiff@0.5.0.patchrenamed and re-attached as@0.6.0-alpha.1.patch. Both hunks (proj4+overantimeridian fix,inferRenderPipelinere-export) still apply unchanged, upstream tickets #366 and PR #374 remain open.New patch
patches/@carbonplan__zarr-layer@0.4.3.patchreplaces two calls tozarr.tryWithConsolidated()withPromise.resolve(baseStore). The helper was removed in zarrita 0.7, and the override above forces 0.7 across the tree, which otherwise surfaced as a runtime(void 0) is not a functioninside_onAddAsyncwhen mounting the legacy ZarrLayer. Consolidated metadata (.zmetadata) is still fetched manually by the library's own_loadV2, so skipping the helper is behavior-preserving.Vite config
optimizeDeps.includeextended with@developmentseed/deck.gl-zarrand itsgeozarr+raster-reprojectleaves, pluszarritaitself.4cf01c5Thanks @yharby! - GPU colormap sprite, histogram slider, and 4-band COG fix.GPU
Colormapsprite with 107 rampsSingle-band COGs and mosaics now render through the v0.6
Colormapshader module sampling@developmentseed/deck.gl-raster/gpu-modules/colormaps.png(256x107 RGBA, matplotlib + rio-tiler + cmocean). Switching ramps is a uniform update oncolormapIndex, no tile re-decode. The CPU baker normalizes band N intocolor.rwithr = 1 + round(t * 254)and reservesr = 0as a nodata sentinel soFilterNoDataVal({ value: 0 })discards those fragments before the ramp sample.New helper module
utils/colormap-sprite.tsdecodes the sprite once per session and caches the uploadedsampler2DArraytexture per luma.glDevicevia aWeakMap. ExportsCOLORMAP_INDEX(all 107 names),COLORMAP_NAMES(sorted),loadColormapSprite(),getColormapTexture(device), andspriteBackgroundStyle(name, heightPx)for CSS previews.CogControls.sveltepreviews every ramp by slicing the sprite as a CSS background-image. Curated 10-ramp "pinned" grid (gray, terrain, viridis, magma, turbo, spectral, inferno, plasma, cividis, rdylgn), plus a search field and a scrollable full list of all 107.Histogram behind the rescale slider
selectCogPipelinenow accepts anonHistogram?: (bins: Uint32Array) => voidcallback. The CPU baker emits a 64-bin histogram (HISTOGRAM_BIN_COUNT) built over the tile's valid samples, stored inCogViewer/StacMosaicVieweras$state.raw<Uint32Array>and rendered byCogControlsas an SVG bar chart behind the rescale sliders. The active[min, max]window draws as a translucent band so the slider visualizes what it is actually clipping.rescaleApplicablenow returnstruewhenbandConfig.mode === 'single'in addition to the legacy uint-RGB case. The single-band path builds its pipeline as[Sampler2DArrayPrecision, FilterNoDataVal, LinearRescale?, Colormap], so the slider stretchescolor.rbefore the ramp lookup.NAIP 4-band opacity fix + dynamic band detection
needsCustomPipelineForConfignow forces the CPU path forgeotiff.count === 4in RGB mode, so the 4th NAIP band is no longer silently interpreted as alpha by the library-default RGBA pipeline.StacMosaicViewerdetects band count +SampleFormatdynamically on the first COG thatMosaicLayer.getSourceresolves (viageotiff.countandcachedTags.sampleFormat), reseedsbandConfigviadefaultBandConfig(count, sf), and updates<CogControls bandCount=...>so 4-band imagery exposes all four bands in the picker. Previously the mosaic hard-coded 3 bands.Sampler2DArrayPrecisionshim@developmentseed/deck.gl-raster@0.6.0-alpha.1'sColormapmodule injectsuniform sampler2DArray colormapTexture;without a precision qualifier, which the Apple-GPU path of luma.gl's WebGL2 backend rejects withERROR: 'sampler2DArray' : No precision specified. Local shimSampler2DArrayPrecision(inutils/cog.ts) injectsprecision highp sampler2DArray;atfs:#decland is chained immediately beforeColormapinbuildCustomRenderTile. Remove once upstream fixes.Dead code removed
Retired
COLOR_RAMP_STOPS,ColorRampId,interpolateRamp,rampToGradientCss, andcustomRenderTilefromutils/cog.ts. All superseded by the sprite path.ColorRampIdis now a type alias forColormapName(all 107 entries).objex-utilsBump coordinated with the main package via the
fixedchangeset config. No new re-exports,colormap-sprite.tsis not published because it depends on luma.glDevice/ WebGL2. Consumers who want GPU colormap rendering should depend on the full@walkthru-earth/objexpackage.439dfd7Thanks @yharby! - Add stac-geoparquet support.objex-utils: newstac-geoparquetmodule with pure transforms that any consumer can use:isStacGeoparquetSchema,stacRowToItem,flattenStacBbox,resolveStacAssetHref,pickStacPrimaryAsset, plusStacGeoparquetRow/StacBboxStruct/StacGeoparquetSchemaColumn/StacRowToItemOptionstypes.objexSvelte lib:ViewerRouterdetects stac-geoparquet via hyparquet schema sniff and routes matching.parquet/.geoparquetfiles toStacTabViewer. A newquery/stac-geoparquet.tshelper uses the existing DuckDB engine (presigned URL, single worker, cancellable) to materialize a STAC FeatureCollection in one shot;StacMosaicViewerconsumes it through the samebuildMosaicSourceMeta+ MosaicLayer path as JSON catalogs.StacTabViewernow shows a "Parquet" badge, relabels the last tab as "Table" (mountingTableViewer), and disables theSTAC Browseriframe button with a tooltip since Radiant Earth stac-browser is JSON-only. Thestac-mapDevSeed iframe handles parquet on its own, so its button is unchanged.