fix: Fix geometry parsing

This commit is contained in:
2026-06-28 00:37:29 +05:00
parent 7c469a524b
commit 1e71b94fdb
5 changed files with 160 additions and 20 deletions

View File

@@ -8,6 +8,7 @@ import (
"encoding/json"
"fmt"
"os/exec"
"path/filepath"
"strings"
)
@@ -56,3 +57,52 @@ func (c *GDALConverter) Footprint(ctx context.Context, src string) ([]byte, erro
}
return info.Wgs84Extent, nil
}
// VectorGeometry reads every feature of a vector file and returns their combined
// geometry as a GeoJSON GeometryCollection reprojected to EPSG:4326, or nil if
// the file has no features. The caller (PostGIS) dissolves the collection into
// the union of all features. Zipped ESRI shapefiles are read in place via GDAL's
// /vsizip/ virtual filesystem; GeoJSON and GeoPackage are read directly.
func (c *GDALConverter) VectorGeometry(ctx context.Context, src string) ([]byte, error) {
input := src
if strings.EqualFold(filepath.Ext(src), ".zip") {
input = "/vsizip/" + src
}
cmd := exec.CommandContext(ctx, "ogr2ogr",
"-f", "GeoJSON",
"-t_srs", "EPSG:4326",
"/vsistdout/", input,
)
var stderr strings.Builder
cmd.Stderr = &stderr
out, err := cmd.Output()
if err != nil {
return nil, fmt.Errorf("ogr2ogr: %w: %s", err, strings.TrimSpace(stderr.String()))
}
var fc struct {
Features []struct {
Geometry json.RawMessage `json:"geometry"`
} `json:"features"`
}
if err := json.Unmarshal(out, &fc); err != nil {
return nil, fmt.Errorf("parse ogr2ogr output: %w", err)
}
geoms := make([]json.RawMessage, 0, len(fc.Features))
for _, f := range fc.Features {
if len(f.Geometry) == 0 || string(f.Geometry) == "null" {
continue
}
geoms = append(geoms, f.Geometry)
}
if len(geoms) == 0 {
return nil, nil
}
return json.Marshal(struct {
Type string `json:"type"`
Geometries []json.RawMessage `json:"geometries"`
}{Type: "GeometryCollection", Geometries: geoms})
}