Filtering and Extracting vector dataΒΆ

WFS also defines mechanisms to only retrieve a subset of the data that matches some specified constraints.

Get Feature by ID

http://localhost:8083/geoserver/wfs?
service=WFS&
version=1.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
featureID=<id>

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeNames=topp:states&featureID=states.46

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection xmlns="http://www.opengis.net/wfs">
   <gml:featureMember>
     <topp:states fid="states.46">
       <topp:the_geom>
         <gml:MultiPolygon srsName="http://www.opengis.net/gml/srs/epsg.xml#4326">
           <gml:polygonMember>
             <gml:Polygon>
               <gml:outerBoundaryIs>
                 <gml:LinearRing>
                   <gml:coordinates xmlns:gml="http://www.opengis.net/gml" decimal="." cs="," ts=" ">
                   -114.046463,38.137691 -114.044273,38.57114
                   <!-- other coordinates skipped -->
                   </gml:coordinates>
                 </gml:LinearRing>
               </gml:outerBoundaryIs>
             </gml:Polygon>
           </gml:polygonMember>
         </gml:MultiPolygon>
       </topp:the_geom>
       <topp:STATE_NAME>Utah</topp:STATE_NAME>
       <topp:STATE_FIPS>49</topp:STATE_FIPS>
       <topp:SUB_REGION>Mtn</topp:SUB_REGION>
       <topp:STATE_ABBR>UT</topp:STATE_ABBR>
       <topp:LAND_KM>212815.546</topp:LAND_KM>
       <topp:WATER_KM>7086.152</topp:WATER_KM>
       <topp:PERSONS>1722850.0</topp:PERSONS>
       <topp:FAMILIES>410862.0</topp:FAMILIES>
       <topp:HOUSHOLD>537273.0</topp:HOUSHOLD>
       <topp:MALE>855759.0</topp:MALE>
       <topp:FEMALE>867091.0</topp:FEMALE>
       <topp:WORKERS>564185.0</topp:WORKERS>
       <topp:DRVALONE>541226.0</topp:DRVALONE>
       <topp:CARPOOL>111197.0</topp:CARPOOL>
       <topp:PUBTRANS>16971.0</topp:PUBTRANS>
       <topp:EMPLOYED>736059.0</topp:EMPLOYED>
       <topp:UNEMPLOY>41389.0</topp:UNEMPLOY>
       <topp:SERVICE>196289.0</topp:SERVICE>
       <topp:MANUAL>102232.0</topp:MANUAL>
       <topp:P_MALE>0.497</topp:P_MALE>
       <topp:P_FEMALE>0.503</topp:P_FEMALE>
       <topp:SAMP_POP>304592.0</topp:SAMP_POP>
     </topp:states>
   </gml:featureMember>
 </wfs:FeatureCollection>

Specifying Attributes of interest

To restrict a GetFeature request by attribute rather than feature, use the propertyName key in the form propertyName=attribute. You can specify a single attribute, or multiple attributes separated by commas.

http://localhost:8083/geoserver/wfs?
service=WFS&
version=1.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
propertyName=<attribute>

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeNames=topp:states&propertyName=STATE_NAME

For a single property from just one feature, use both featureID and propertyName:

http://localhost:8083/geoserver/wfs?
service=WFS&
version=1.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
feaureID=<id>&
propertyName=<attribute>

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeNames=topp:states&featureID=states.42&propertyName=STATE_NAME

To obtain the attributes STATE_NAME and PERSONS one can use:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeNames=topp:states&featureID=states.42&propertyName=STATE_NAME,PERSONS

1
2
3
4
5
6
7
8
9
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection xmlns="http://www.opengis.net/wfs">
   <gml:featureMember>
     <topp:states fid="states.42">
       <topp:STATE_NAME>Rhode Island</topp:STATE_NAME>
       <topp:PERSONS>1003464.0</topp:PERSONS>
     </topp:states>
   </gml:featureMember>
 </wfs:FeatureCollection>

Limiting Features

If the ID of the feature is unknown but one still wants to limit the number of features returned, use the count parameter for WFS 2.0.0 or the maxFeatures parameter for earlier WFS versions:

http://localhost:8083/geoserver/wfs?
service=WFS&
version=2.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
count=<N>

or

http://localhost:8083/geoserver/wfs?
service=WFS&
version=1.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
maxFeatures=<N>

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeNames=topp:states&maxFeatures=3&propertyName=STATE_NAME

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection xmlns="http://www.opengis.net/wfs">
   <gml:featureMember>
     <topp:states fid="states.1">
       <topp:STATE_NAME>Illinois</topp:STATE_NAME>
     </topp:states>
   </gml:featureMember>
   <gml:featureMember>
     <topp:states fid="states.2">
       <topp:STATE_NAME>District of Columbia</topp:STATE_NAME>
     </topp:states>
   </gml:featureMember>
   <gml:featureMember>
     <topp:states fid="states.3">
       <topp:STATE_NAME>Delaware</topp:STATE_NAME>
     </topp:states>
   </gml:featureMember>
 </wfs:FeatureCollection>

Sorting

Exactly which N features will be returned depends in the internal structure of the data. However, you can sort the returned selection based on an attribute value.

http://localhost:8083/geoserver/wfs?
service=WFS&
version=2.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
count=<N>&
sortBy=<attribute>[ D]

Optionally you can add `` D`` to the name of the attribute to sort in descending order (in a URL it will look +D where the plus escapes the space).

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.1.0&request=GetFeature&typeNames=topp:states&maxFeatures=3&propertyName=STATE_NAME&sortBy=PERSONS

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection>
   <gml:featureMembers>
     <topp:states gml:id="states.47">
       <topp:STATE_NAME>California</topp:STATE_NAME>
     </topp:states>
     <topp:states gml:id="states.39">
       <topp:STATE_NAME>New York</topp:STATE_NAME>
     </topp:states>
     <topp:states gml:id="states.15">
       <topp:STATE_NAME>Texas</topp:STATE_NAME>
     </topp:states>
   </gml:featureMembers>
 </wfs:FeatureCollection>

http://localhost:8083/geoserver/wfs?service=WFS&version=1.1.0&request=GetFeature&typeNames=topp:states&maxFeatures=3&propertyName=STATE_NAME&sortBy=PERSONS+D

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection>
   <gml:featureMembers>
     <topp:states gml:id="states.29">
       <topp:STATE_NAME>Wyoming</topp:STATE_NAME>
     </topp:states>
     <topp:states gml:id="states.32">
       <topp:STATE_NAME>Vermont</topp:STATE_NAME>
     </topp:states>
     <topp:states gml:id="states.2">
       <topp:STATE_NAME>District of Columbia</topp:STATE_NAME>
     </topp:states>
   </gml:featureMembers>
 </wfs:FeatureCollection>

BBOX filter

The BBOX parameter allows you to search for features that are contained (or partially contained) inside a box of user-defined coordinates.

http://example.com/geoserver/wfs?
service=WFS&
version=1.0.0&
request=GetFeature&
typeNames=<namespace>:<featuretype>&
bbox=<a1>,<b1>,<a2>,<b2>

Example:

http://localhost:8083/geoserver/wfs?service=WFS&version=1.1.0&request=GetFeature&typeNames=topp:states&bbox=-70,40,-60,50&propertyName=STATE_NAME

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:wfs="http://www.opengis.net/wfs" xmlns:gml="http://www.opengis.net/gml" xmlns:topp="http://www.openplans.org/topp" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" numberOfFeatures="2" timeStamp="2022-10-11T10:31:26.158Z" xsi:schemaLocation="http://www.opengis.net/wfs http://localhost:8080/geoserver/schemas/wfs/1.1.0/wfs.xsd http://www.openplans.org/topp http://localhost:8080/geoserver/wfs?service=WFS&amp;version=1.1.0&amp;request=DescribeFeatureType&amp;typeName=topp%3Astates">
   <gml:featureMembers>
     <topp:states gml:id="states.26">
       <topp:STATE_NAME>Maine</topp:STATE_NAME>
     </topp:states>
     <topp:states gml:id="states.37">
       <topp:STATE_NAME>Massachusetts</topp:STATE_NAME>
     </topp:states>
   </gml:featureMembers>
 </wfs:FeatureCollection>

CQL Filter

To filter features we can also use a language called CQL. Copy the following URL in your browser’s navigation bar:

http://localhost:8083/geoserver/wfs?request=GetFeature&service=WFS&version=1.0.0&typeName=topp:states&outputFormat=GML2&CQL_FILTER=STATE_ABBR=%27CO%27

The results shows only Colorado:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
 <?xml version="1.0" encoding="UTF-8"?>
 <wfs:FeatureCollection>
   <gml:boundedBy>
     <gml:null>unknown</gml:null>
   </gml:boundedBy>
   <gml:featureMember>
     <topp:states fid="states.6">
       <topp:the_geom>
         <gml:MultiPolygon srsName="http://www.opengis.net/gml/srs/epsg.xml#4326">
           <gml:polygonMember>
             <gml:Polygon>
               <gml:outerBoundaryIs>
                 <gml:LinearRing>
                   <gml:coordinates xmlns:gml="http://www.opengis.net/gml" decimal="." cs="," ts=" ">
                   <!-- Coordinates skipped for brevity -->
                   </gml:coordinates>
                 </gml:LinearRing>
               </gml:outerBoundaryIs>
             </gml:Polygon>
           </gml:polygonMember>
         </gml:MultiPolygon>
       </topp:the_geom>
       <topp:STATE_NAME>Colorado</topp:STATE_NAME>
       <topp:STATE_FIPS>08</topp:STATE_FIPS>
       <topp:SUB_REGION>Mtn</topp:SUB_REGION>
       <topp:STATE_ABBR>CO</topp:STATE_ABBR>
       <topp:LAND_KM>268659.501</topp:LAND_KM>
       <topp:WATER_KM>960.364</topp:WATER_KM>
       <topp:PERSONS>3294394.0</topp:PERSONS>
       <topp:FAMILIES>854214.0</topp:FAMILIES>
       <topp:HOUSHOLD>1282489.0</topp:HOUSHOLD>
       <topp:MALE>1631295.0</topp:MALE>
       <topp:FEMALE>1663099.0</topp:FEMALE>
       <topp:WORKERS>1233023.0</topp:WORKERS>
       <topp:DRVALONE>1216639.0</topp:DRVALONE>
       <topp:CARPOOL>210274.0</topp:CARPOOL>
       <topp:PUBTRANS>46983.0</topp:PUBTRANS>
       <topp:EMPLOYED>1633281.0</topp:EMPLOYED>
       <topp:UNEMPLOY>99438.0</topp:UNEMPLOY>
       <topp:SERVICE>421079.0</topp:SERVICE>
       <topp:MANUAL>181760.0</topp:MANUAL>
       <topp:P_MALE>0.495</topp:P_MALE>
       <topp:P_FEMALE>0.505</topp:P_FEMALE>
       <topp:SAMP_POP>512677.0</topp:SAMP_POP>
     </topp:states>
   </gml:featureMember>
 </wfs:FeatureCollection>

It’s also possible to perform the same filter using a XML POST request to http://localhost:8083/geoserver/wfs. This allows for more complex filters to be included (e.g., a polygon intersection filter, against a geometry with many coordinates).

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
 <?xml version="1.0"?>
 <wfs:GetFeature xmlns:topp="http://www.openplans.org/topp"
                 xmlns:wfs="http://www.opengis.net/wfs"
                 xmlns:ogc="http://www.opengis.net/ogc"
                 xmlns:gml="http://www.opengis.net/gml"
                 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                 service="WFS" version="1.0.0" outputFormat="GML2"
                 xsi:schemaLocation="http://www.opengis.net/wfs http://schemas.opengis.net/wfs/1.0.0/WFS-basic.xsd">
   <wfs:Query typeName="topp:states">
     <ogc:PropertyName>topp:STATE_NAME</ogc:PropertyName>
     <ogc:PropertyName>topp:LAND_KM</ogc:PropertyName>
     <ogc:PropertyName>topp:the_geom</ogc:PropertyName>
     <ogc:Filter>
       <ogc:PropertyIsEqualTo>
         <ogc:PropertyName>topp:STATE_ABBR</ogc:PropertyName>
         <ogc:Literal>CO</ogc:Literal>
       </ogc:PropertyIsEqualTo>
     </ogc:Filter>
   </wfs:Query>
 </wfs:GetFeature>

In this section we will see how to edit the features via a protocol called WFS Transactional (WFS-T).