[gdal-dev] how to implement user specified events and handlers

Even Rouault even.rouault at mines-paris.org
Tue Oct 15 11:10:08 PDT 2013


Martin,

The closest equivalent in the GDAL/OGR code base I could think of is the 
possibility of defining a custom error handler from the Python bindings.

Basically you would need to have a C API to register a C callback, 
"VFKLineCallbackRegister", and you would have a Python C module that would 
define such a C callback "PyVFKCallbackWrapper" (or extend the existing GDAL 
Python bindings), that would be a wrapper that would take a Python callable 
object as argument and call it. And you would have a C function, exposed as 
Python, "RegisterVFKCallback" that would pass PyVFKCallbackWrapper to 
VFKLineCallbackRegister with the Python function as a userdata.

The relevant existing code is in :

* swig/include/port.i :

/* Equivalent of PyVFKCallbackWrapper */
%{
void CPL_STDCALL PyCPLErrorHandler(CPLErr eErrClass, int err_no, const char* 
pszErrorMsg)
{
    void* user_data = CPLGetErrorHandlerUserData();
    PyObject *psArgs;

    psArgs = Py_BuildValue("(iis)", eErrClass, err_no, pszErrorMsg );
    PyEval_CallObject( (PyObject*)user_data, psArgs);
    Py_XDECREF(psArgs);
}
%}

/* Equivalent of RegisterVFKCallback */
%inline %{
  CPLErr PushErrorHandler( CPLErrorHandler pfnErrorHandler = NULL, void* 
user_data = NULL )
  {
[...]
        CPLPushErrorHandlerEx(pfnErrorHandler, user_data);  /* equivalent of 
VFKLineCallbackRegister */
    return CE_None;
  }
%}

* swig/include/python/typemaps_python.i :

%typemap(in) ( CPLErrorHandler pfnErrorHandler = NULL, void* user_data = NULL 
) 
{
    /* %typemap(in) (CPLErrorHandler pfnErrorHandler = NULL, void* user_data = 
NULL) */
    [...]
     if (!PyCallable_Check($input))
    {
        PyErr_SetString( PyExc_RuntimeError, 
                         "Object given is not a String or a Python function" 
);
        SWIG_fail;
    }
    else
    {
        Py_INCREF($input);
        $1 = PyCPLErrorHandler;
        $2 = $input;
    }
}

Best regards,

Even

> Hi all,
> 
> I wonder if there is a way how to implement mechanism for
> user-specified events and handlers in GDAL/OGR.
> 
> I am implementing a Python script which checks VFK file using OGR
> driver [1]. This script reads VFK data and stores them in SQLite
> database which is created by the OGR driver.
> 
> Beside some geometry checks the script should do some extra
> user-defined checks on the original VFK file. To avoid double reading
> of the file (first by the script and then by the OGR driver) I would
> like to use mechanism of events and handlers. In other words, event
> for reading a new line from the VFK file [2] and the handler (callback
> subroutine in Python script) which would do some extra checks on the
> line [3].
> 
> Any idea how it should be correctly implemented in VFK driver and the
> Python script? Thanks a lot for any hits in advance!
> 
> Martin
> 
> [1] http://gdal.org/ogr/drv_vfk.html
> [2]
> http://trac.osgeo.org/gdal/browser/trunk/gdal/ogr/ogrsf_frmts/vfk/vfkreade
> r.cpp#L125 [3]
> https://github.com/landam/ogr-vfk-testing/blob/master/read-vfk-test/read-v
> fk.py#L52

-- 
Geospatial professional services
http://even.rouault.free.fr/services.html


More information about the gdal-dev mailing list