1

I'm getting this error on the ST_ConcaveHull function call and after reading the docs, I'm unclear as to whether this Error is correct behavior or not.

Here is the business end of the query (vx are points):
select id , ST_ConcaveHull(ST_Collect(vx), 0.80)

And here's the error:

********** Error **********  
ERROR: ExteriorRing: geom is not a polygon  
SQL state: XX000  
Context: PL/pgSQL function st_concavehull(geometry,double precision,boolean) line 67 at assignment

Since I'm not passing polygons of any sort, I assume the ST_ConcaveHull function is creating them internally. I assume that there must be 1 or more grouping of points that don't produce an expected polygon. And this wouldn't surprise me, but I'd rather just get back a null geometry rather than an error that borks the query.

Is the behaviour as-designed, and if so, what is the best way to isolate the data that is causing the error (I assume I would need to pre-filter the data somehow)?

I can also tell you that
select id , ST_ConcaveHull(ST_Collect(vx), 0.99) completes successfully.

PostGIS Version:

POSTGIS="2.0.4" GEOS="3.4.2-CAPI-1.8.2 r0" PROJ="Rel. 4.8.0, 6 March 2012" GDAL="GDAL 1.10.0, released 2013/04/24" LIBXML="2.7.8" LIBJSON="UNKNOWN" (core procs from "2.0.4" need upgrade) RASTER (raster procs from "2.0.4" need upgrade)

Postgresql Version:

PostgreSQL 9.2.2, compiled by Visual C++ build 1600, 64-bit

3
  • 2
    It's a bug. Can you ticket this one in our ticket tracker with a sample dataset and I'll take a look at it. postgis.net/support Thanks, Regina
    – LR1234567
    Jul 11, 2014 at 4:27
  • I'm trying to create a sample dataset that I can make public, but everything I create ends up working with the above ST_ConcaveHull call. It's maddening! Jul 11, 2014 at 13:31
  • Done. trac.osgeo.org/postgis/ticket/2836 Jul 11, 2014 at 15:09

2 Answers 2

2

Regina's comment actually answered the question--it isn't expected behaviour.

As a workaround, I wrapped the call with function w/ exception block so that I get null back (which is OK for my purposes).

Feel free to edit/improve because pl/pgsql isn't my strength:

 --DROP FUNCTION public.st_nullableconcavehull(geometry, double precision, boolean);

CREATE OR REPLACE FUNCTION public.st_nullableconcavehull(param_geom geometry, param_pctconvex double precision, param_allow_holes boolean DEFAULT false)
  RETURNS geometry AS
$BODY$
    DECLARE
    BEGIN       
            RETURN public.st_concavehull(param_geom,param_pctconvex,param_allow_holes);
        EXCEPTION when others then RETURN null;
    END;
$BODY$
  LANGUAGE plpgsql IMMUTABLE STRICT
  COST 100;
ALTER FUNCTION public.st_nullableconcavehull(geometry, double precision, boolean)
  OWNER TO postgres;
COMMENT ON FUNCTION public.st_nullableconcavehull(geometry, double precision, boolean) IS 'args: geomA, target_percent, allow_holes=false - The concave hull of a geometry represents a possibly concave geometry that encloses all geometries within the set. You can think of it as shrink wrapping.';
0

I confirm this behavior is still problematic as of this postgis_full_version() on PostgreSQL 9.5

POSTGIS="2.3.2 r15302" GEOS="3.4.2-CAPI-1.8.2 r3921" PROJ="Rel. 4.8.0, 6 March 2012" GDAL="GDAL 1.10.1, released 2013/08/26" LIBXML="2.9.1" LIBJSON="0.11.99" RASTER.

Jay Cummins Patch was effective however with my data-set I encountered case where ST_ConcaveHull() could return MultiLineString instead of MultiPolygon which would trigger others errors in post processing of such geometries.

To avoid this I altered his script so that nullableconcavehull() return NULL if returned object is not of MultiPolygon type. Here is the altered code.

CREATE OR REPLACE FUNCTION public.st_nullableconcavehull(param_geom geometry, param_pctconvex double precision, param_allow_holes boolean DEFAULT false)
  RETURNS geometry AS
$BODY$
    --Curtesy of Jay Cummins http://gis.stackexchange.com/questions/106854
    DECLARE
    rgeom geometry;
    BEGIN       
            SELECT public.st_concavehull(param_geom,param_pctconvex,param_allow_holes) INTO rgeom;

            --RAISE DEBUG 'Geometry type : % ', st_geometrytype(rgeom);
            IF st_geometrytype(rgeom)='ST_Polygon'
            THEN RETURN rgeom;
            ELSE RETURN null;
        END IF;

        EXCEPTION when others then RETURN null;
    END;
$BODY$
  LANGUAGE plpgsql IMMUTABLE STRICT
  COST 100;
ALTER FUNCTION public.st_nullableconcavehull(geometry, double precision, boolean)  OWNER TO postgres;
COMMENT ON FUNCTION public.st_nullableconcavehull(geometry, double precision, boolean) IS 'args: geomA, target_percent, allow_holes=false - The concave hull of a geometry represents a possibly concave geometry that encloses all geometries within the set. You can think of it as shrink wrapping.';

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.