WMS – Get a WMS GetFeatureInfo Response with MapServer in JSON Format

getfeatureinfojsonmapserverwms

I use Mapserver with the Leaflet JS library and I want to display some attributes informations of a raster file by clicking on the map.
Therefore I use the GetFeatureInfo WMS request in order to return these informations.
I managed to get the infos with the text/html format but I'd like to get a JSON response back in my browser, e.g :

{
    "value": 14.5, // I must precise I use GetFeatureInfo on a raster and the value result corresponds to the value of the pixel 
}

BELOW ARE THE UPDATES :

So I changed the wms_get_feature_info_formalist in the METADATA bloc of my mapfile :

"wms_getfeatureinfo_formatlist" "application/json"

Then, I edited my template as following to return the value of the pixel :

<!-- MapServer Template -->
{
    "value": [value_0] // [value_0] allow the user to get the value of a pixel
}

I edited the mapfile with the OUTPUT format parameter in order to use the JSON format :

OUTPUTFORMAT
  NAME "json"
  MIMETYPE "application/json"
  DRIVER "TEMPLATE"
  FORMATOPTION "FILE=template.js"
END

And as it is written in the docs, I set :

TEMPLATE "EMPTY"

My GetFeatureInfo request is the one (see "application/json" specified in the INFO_FORMAT parameter)

http://IP/cgi-bin/mapserv?map=/var/www/html/mapfiles/test1.map&SERVICE=WMS&VERSION=1.1.1&REQUEST=GetFeatureInfo&BBOX=465348.6282001531,5431156.607774916,697564.3201305186,5503160.28841955&SRS=EPSG:3857&WIDTH=1519&HEIGHT=471&LAYERS=layer1&STYLES=&FORMAT=image/png&TRANSPARENT=true&QUERY_LAYERS=layer1&INFO_FORMAT=application/json&X=766&Y=261

But when I try the GetFeatureInfo request, my browser returns a JSON response but with the following error message :

SyntaxError: JSON.parse: unexpected character at line 2 column 11 of
the JSON data

It seems the [value_0] is not recognized in JSON whereas it works well with the text/html format..
How could I do to make it work ?
I'm really stuck and any help would be greatly appreciated !

Best Answer

There is a working example of a raster layer with a GetFeatureInfo query returning GeoJSON at https://app.mapserverstudio.net/#fXO3XBRn No templates are required, just the OUTPUTFORMAT:

    OUTPUTFORMAT
        NAME "geojson"
        DRIVER "OGR/GEOJSON"
        MIMETYPE "application/json; subtype=geojson; charset=utf-8"
        FORMATOPTION "FORM=SIMPLE"
        FORMATOPTION "STORAGE=memory"
        FORMATOPTION "LCO:NATIVE_MEDIA_TYPE=application/vnd.geo+json"
    END

    WEB
        METADATA
            "wms_enable_request" "*"
            # ensure the outputformat is in this list below
            "wms_getfeatureinfo_formatlist" "geojson"
        END
    END

Counter intuitively the "gml_include_items" is important at the LAYER level even though it is for a raster layer.

    LAYER
        NAME "hillsahde"
        STATUS ON
        TYPE RASTER
        DATA "/data/copernicus/eu_dem_v11_E10N00.TIF"
        PROCESSING "BANDS=1"
        CLASS
            STYLE
                COLORRANGE "#abc270" "#f7f1e5"
                DATARANGE 0 2000
            END
        END
        TEMPLATE "ttt"
        METADATA
            "gml_include_items" "all"
            "gml_types" "auto"
        END
    END

A sample request is:

https://api.mapserverstudio.net/mapserver/?map=/etc/mapserver/mapfiles/output/f920137d-5f1d-4ac4-9bf4-4a86bf4f2b7e.map&SERVICE=WMS&VERSION=1.3.0&REQUEST=GetFeatureInfo&FORMAT=image/png&TRANSPARENT=true&QUERY_LAYERS=hillsahde&LAYERS=hillsahde&STYLES=&FILTER=&INFO_FORMAT=geojson&I=50&J=50&CRS=EPSG:3857&WIDTH=101&HEIGHT=101&BBOX=1799862.1893692566,967876.9675296084,1801451.8980644122,969466.6762247642&_dc=1694810648114

GeoJSON response

This returns the following GeoJSON:

{
"type": "FeatureCollection",
"name": "hillsahde",
"crs": { "type": "name", "properties": { "name": "urn:ogc:def:crs:EPSG::3857" } },
"features": [
{ "type": "Feature", "properties": { "x": "1800662.5", "y": "968662.5", "value_0": "1349.0573", "value_list": "1349.0573", "class": "0", "red": "-1", "green": "-1", "blue": "-1" }, "geometry": { "type": "Point", "coordinates": [ 1800662.5, 968662.5 ] } }
]
}

You can construct and call this URL with JavaScript with a fetch call (or older style AJAX call) and you can do whatever you want with the GeoJSON in the browser. In the example above the GeoJSON is displayed in a grid when the map is clicked. This functionality is part of a client like OpenLayers - https://openlayers.org/en/latest/examples/getfeatureinfo-tile.html

Related Question