bbox_map_server/
wms_capabilities.rs

1use serde::Deserialize;
2
3#[derive(Deserialize, Debug)]
4#[serde(rename = "WMS_Capabilities")]
5pub struct WmsCapabilities {
6    pub version: String,
7    #[serde(rename = "Service")]
8    pub service: Service,
9    #[serde(rename = "Capability")]
10    pub capability: Capability,
11}
12
13#[derive(Deserialize, Debug)]
14#[serde(rename_all = "PascalCase")]
15pub struct Service {
16    pub name: String,
17    pub title: String,
18    pub keyword_list: Option<KeywordList>,
19    //...
20}
21
22#[derive(Deserialize, Debug)]
23pub struct KeywordList {
24    #[serde(rename = "Keyword", default)]
25    pub keywords: Vec<String>,
26}
27
28#[derive(Deserialize, Debug)]
29pub struct Capability {
30    #[serde(rename = "Request")]
31    pub request: Request,
32    // Exception
33    // UserDefinedSymbolization
34    #[serde(rename = "Layer", default)]
35    pub layers: Vec<Layer>,
36    // QGIS extended capabilities
37    // WFSLayers
38    // LayerDrawingOrder
39}
40
41#[derive(Deserialize, Debug)]
42#[serde(rename_all = "PascalCase")]
43pub struct Request {
44    pub get_map: Option<RequestType>,
45    pub get_feature_info: Option<RequestType>,
46    pub get_capabilities: Option<RequestType>,
47    pub get_legend_graphic: Option<RequestType>,
48    pub get_styles: Option<RequestType>,
49    pub describe_layer: Option<RequestType>,
50    // QGIS extended capabilities
51    pub get_print: Option<RequestType>,
52}
53
54#[derive(Deserialize, Debug)]
55pub struct RequestType {
56    #[serde(rename = "Format", default)]
57    pub format: Vec<String>,
58    #[serde(rename = "DCPType")]
59    pub dcp_type: DcpType,
60}
61
62#[derive(Deserialize, Debug)]
63pub struct DcpType {
64    #[serde(rename = "HTTP")]
65    pub http: Http,
66}
67
68#[derive(Deserialize, Debug)]
69#[serde(rename_all = "PascalCase")]
70pub struct Http {
71    pub get: Option<Verb>,
72    pub post: Option<Verb>,
73}
74
75#[derive(Deserialize, Debug)]
76pub struct Verb {
77    #[serde(rename = "OnlineResource")]
78    pub online_resource: OnlineResource,
79}
80
81#[derive(Deserialize, Debug)]
82pub struct Layer {
83    pub queryable: Option<bool>,
84    pub opaque: Option<bool>,
85    pub cascaded: Option<bool>,
86    #[serde(rename = "Name")]
87    pub name: Option<String>,
88    #[serde(rename = "Title")]
89    pub title: Option<String>,
90    #[serde(rename = "Abstract")]
91    pub abstract_: Option<String>,
92
93    #[serde(rename = "CRS", default)]
94    pub crs: Vec<String>,
95    #[serde(rename = "EX_GeographicBoundingBox")]
96    pub ex_geographic_bounding_box: Option<ExGeographicBoundingBox>,
97    #[serde(rename = "BoundingBox", default)]
98    pub bounding_box: Vec<BoundingBox>,
99    // pub Style
100    #[serde(rename = "MinScaleDenominator")]
101    pub min_scale_denominator: Option<f32>,
102    #[serde(rename = "MaxScaleDenominator")]
103    pub max_scale_denominator: Option<f32>,
104
105    #[serde(rename = "Attribution")]
106    pub attribution: Option<Attribution>,
107    #[serde(rename = "DataURL")]
108    pub data_url: Option<MetadataUrl>,
109    #[serde(rename = "MetadataURL")]
110    pub metadata_url: Option<MetadataUrl>,
111    #[serde(rename = "Layer", default)]
112    pub layers: Vec<Layer>,
113
114    // QGIS extended capabilities
115    pub visible: Option<bool>,
116    pub opacity: Option<f32>,
117    pub expanded: Option<bool>,
118    #[serde(rename = "mutuallyExclusive")]
119    pub mutually_exclusive: Option<bool>,
120    #[serde(rename = "displayField")]
121    pub display_field: Option<String>,
122    #[serde(rename = "geometryType")]
123    pub geometry_type: Option<String>,
124    // pub TreeName
125    // pub PrimaryKey
126    // pub Attributes
127}
128
129#[derive(Deserialize, Debug)]
130#[serde(rename_all = "camelCase")]
131pub struct ExGeographicBoundingBox {
132    pub west_bound_longitude: f64,
133    pub east_bound_longitude: f64,
134    pub south_bound_latitude: f64,
135    pub north_bound_latitude: f64,
136}
137
138#[derive(Deserialize, Debug)]
139pub struct BoundingBox {
140    #[serde(rename = "CRS")]
141    pub crs: String,
142    pub minx: f64,
143    pub miny: f64,
144    pub maxx: f64,
145    pub maxy: f64,
146}
147
148#[derive(Deserialize, Debug)]
149#[serde(rename_all = "PascalCase")]
150pub struct Attribution {
151    pub title: String,
152    pub online_resource: OnlineResource,
153}
154
155#[derive(Deserialize, Debug)]
156#[serde(rename_all = "PascalCase")]
157pub struct MetadataUrl {
158    pub online_resource: OnlineResource,
159    // type
160    // Format
161}
162
163#[derive(Deserialize, Debug)]
164pub struct OnlineResource {
165    pub href: String,
166    // xlink
167    // type
168}
169
170#[cfg(test)]
171mod test {
172    use super::*;
173    use serde_xml_rs::from_reader;
174
175    #[test]
176    fn umn() {
177        let s = r#"<?xml version='1.0' encoding="UTF-8" standalone="no" ?>
178<WMS_Capabilities version="1.3.0"  xmlns="http://www.opengis.net/wms"   xmlns:sld="http://www.opengis.net/sld"   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"   xmlns:ms="http://mapserver.gis.umn.edu/mapserver"   xsi:schemaLocation="http://www.opengis.net/wms http://schemas.opengis.net/wms/1.3.0/capabilities_1_3_0.xsd  http://www.opengis.net/sld http://schemas.opengis.net/sld/1.1.0/sld_capabilities.xsd  http://mapserver.gis.umn.edu/mapserver http://localhost/cgi-bin/mapserv?service=WMS&amp;version=1.3.0&amp;request=GetSchemaExtension">
179
180<!-- MapServer version 7.4.3 OUTPUT=PNG OUTPUT=JPEG OUTPUT=KML SUPPORTS=PROJ SUPPORTS=AGG SUPPORTS=FREETYPE SUPPORTS=CAIRO SUPPORTS=SVG_SYMBOLS SUPPORTS=RSVG SUPPORTS=ICONV SUPPORTS=FRIBIDI SUPPORTS=WMS_SERVER SUPPORTS=WMS_CLIENT SUPPORTS=WFS_SERVER SUPPORTS=WFS_CLIENT SUPPORTS=WCS_SERVER SUPPORTS=SOS_SERVER SUPPORTS=FASTCGI SUPPORTS=THREADS SUPPORTS=GEOS SUPPORTS=PBF INPUT=JPEG INPUT=POSTGIS INPUT=OGR INPUT=GDAL INPUT=SHAPEFILE -->
181
182<Service>
183  <Name>WMS</Name>
184  <Title>Test mapfile for MVT development.</Title>
185  <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/>
186  <ContactInformation>
187  </ContactInformation>
188  <MaxWidth>4096</MaxWidth>
189  <MaxHeight>4096</MaxHeight>
190</Service>
191
192<Capability>
193  <Request>
194    <GetCapabilities>
195      <Format>text/xml</Format>
196      <DCPType>
197        <HTTP>
198          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
199          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
200        </HTTP>
201      </DCPType>
202    </GetCapabilities>
203    <GetMap>
204      <Format>image/png; mode=8bit</Format>
205      <Format>application/x-protobuf</Format>
206      <Format>image/png</Format>
207      <Format>image/jpeg</Format>
208      <Format>image/vnd.jpeg-png</Format>
209      <Format>image/vnd.jpeg-png8</Format>
210      <Format>application/x-pdf</Format>
211      <Format>image/svg+xml</Format>
212      <Format>image/tiff</Format>
213      <Format>application/vnd.google-earth.kml+xml</Format>
214      <Format>application/vnd.google-earth.kmz</Format>
215      <Format>application/json</Format>
216      <DCPType>
217        <HTTP>
218          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
219          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
220        </HTTP>
221      </DCPType>
222    </GetMap>
223    <GetFeatureInfo>
224      <Format>text/plain</Format>
225      <Format>application/vnd.ogc.gml</Format>
226      <DCPType>
227        <HTTP>
228          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
229          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
230        </HTTP>
231      </DCPType>
232    </GetFeatureInfo>
233    <sld:DescribeLayer>
234      <Format>text/xml</Format>
235      <DCPType>
236        <HTTP>
237          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
238          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
239        </HTTP>
240      </DCPType>
241    </sld:DescribeLayer>
242    <sld:GetLegendGraphic>
243      <Format>image/png; mode=8bit</Format>
244      <Format>image/png</Format>
245      <Format>image/jpeg</Format>
246      <Format>image/vnd.jpeg-png</Format>
247      <Format>image/vnd.jpeg-png8</Format>
248      <DCPType>
249        <HTTP>
250          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
251          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
252        </HTTP>
253      </DCPType>
254    </sld:GetLegendGraphic>
255    <ms:GetStyles>
256      <Format>text/xml</Format>
257      <DCPType>
258        <HTTP>
259          <Get><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Get>
260          <Post><OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://localhost/cgi-bin/mapserv?"/></Post>
261        </HTTP>
262      </DCPType>
263    </ms:GetStyles>
264  </Request>
265  <Exception>
266    <Format>XML</Format>
267    <Format>INIMAGE</Format>
268    <Format>BLANK</Format>
269  </Exception>
270  <sld:UserDefinedSymbolization SupportSLD="1" UserLayer="0" UserStyle="1" RemoteWFS="0" InlineFeature="0" RemoteWCS="0"/>
271  <Layer>
272    <Name>ne_countries</Name>
273    <Title>Test mapfile for MVT development.</Title>
274    <Abstract>ne_countries</Abstract>
275    <CRS>epsg:3857</CRS>
276    <CRS>epsg:4326</CRS>
277    <EX_GeographicBoundingBox>
278        <westBoundLongitude>-8.98315e-06</westBoundLongitude>
279        <eastBoundLongitude>-8.98315e-06</eastBoundLongitude>
280        <southBoundLatitude>-8.98315e-06</southBoundLatitude>
281        <northBoundLatitude>-8.98315e-06</northBoundLatitude>
282    </EX_GeographicBoundingBox>
283    <BoundingBox CRS="EPSG:3857"
284                minx="-1" miny="-1" maxx="-1" maxy="-1" />
285    <Layer queryable="0" opaque="0" cascaded="0">
286        <Name>country</Name>
287        <Title>country</Title>
288        <CRS>epsg:4326</CRS>
289        <CRS>epsg:3857</CRS>
290        <CRS>epsg:900913</CRS>
291        <EX_GeographicBoundingBox>
292            <westBoundLongitude>-180</westBoundLongitude>
293            <eastBoundLongitude>180</eastBoundLongitude>
294            <southBoundLatitude>-89.5014</southBoundLatitude>
295            <northBoundLatitude>83.6341</northBoundLatitude>
296        </EX_GeographicBoundingBox>
297        <BoundingBox CRS="epsg:4326"
298                    minx="-89.5014" miny="-180" maxx="83.6341" maxy="180" />
299        <MetadataURL type="TC211">
300          <Format>text/xml</Format>
301          <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://localhost/cgi-bin/mapserv?request=GetMetadata&amp;layer=country"/>
302        </MetadataURL>
303    </Layer>
304  </Layer>
305</Capability>
306</WMS_Capabilities>
307    "#;
308        let cap: WmsCapabilities = from_reader(s.as_bytes()).unwrap();
309        println!("{:#?}", cap);
310
311        assert_eq!(cap.version, "1.3.0");
312        assert_eq!(cap.service.name, "WMS");
313        assert_eq!(cap.service.title, "Test mapfile for MVT development.");
314
315        assert_eq!(
316            cap.capability.layers[0].name,
317            Some("ne_countries".to_string())
318        );
319        assert_eq!(
320            cap.capability.layers[0].title,
321            Some("Test mapfile for MVT development.".to_string())
322        );
323        assert_eq!(
324            cap.capability.layers[0].abstract_,
325            Some("ne_countries".to_string())
326        );
327        assert_eq!(cap.capability.layers[0].crs, vec!["epsg:3857", "epsg:4326"]);
328
329        let layer = &cap.capability.layers[0].layers[0];
330        assert_eq!(layer.name, Some("country".to_string()));
331        assert_eq!(
332            layer.metadata_url.as_ref().unwrap().online_resource.href,
333            "http://localhost/cgi-bin/mapserv?request=GetMetadata&layer=country"
334        );
335        assert_eq!(layer.crs, vec!["epsg:4326", "epsg:3857", "epsg:900913"]);
336    }
337
338    #[test]
339    fn qgis() {
340        let s = r#"<?xml version="1.0" encoding="utf-8"?>
341<WMS_Capabilities xmlns:sld="http://www.opengis.net/sld" version="1.3.0" xmlns="http://www.opengis.net/wms" xmlns:qgs="http://www.qgis.org/wms" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.opengis.net/wms http://schemas.opengis.net/wms/1.3.0/capabilities_1_3_0.xsd http://www.opengis.net/sld http://schemas.opengis.net/sld/1.1.0/sld_capabilities.xsd http://www.qgis.org/wms http://127.0.0.1:8080/wms/qgs/ne?SERVICE=WMS&amp;REQUEST=GetSchemaExtension">
342 <Service>
343  <Name>WMS</Name>
344  <Title>untitled</Title>
345  <KeywordList>
346   <Keyword vocabulary="ISO">infoMapAccessService</Keyword>
347  </KeywordList>
348  <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne"/>
349  <Fees>conditions unknown</Fees>
350  <AccessConstraints>None</AccessConstraints>
351 </Service>
352 <Capability>
353  <Request>
354   <GetCapabilities>
355    <Format>text/xml</Format>
356    <DCPType>
357     <HTTP>
358      <Get>
359       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
360      </Get>
361     </HTTP>
362    </DCPType>
363   </GetCapabilities>
364   <GetMap>
365    <Format>image/jpeg</Format>
366    <Format>image/png</Format>
367    <Format>image/png; mode=16bit</Format>
368    <Format>image/png; mode=8bit</Format>
369    <Format>image/png; mode=1bit</Format>
370    <Format>application/dxf</Format>
371    <DCPType>
372     <HTTP>
373      <Get>
374       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
375      </Get>
376     </HTTP>
377    </DCPType>
378   </GetMap>
379   <GetFeatureInfo>
380    <Format>text/plain</Format>
381    <Format>text/html</Format>
382    <Format>text/xml</Format>
383    <Format>application/vnd.ogc.gml</Format>
384    <Format>application/vnd.ogc.gml/3.1.1</Format>
385    <Format>application/json</Format>
386    <Format>application/geo+json</Format>
387    <DCPType>
388     <HTTP>
389      <Get>
390       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
391      </Get>
392     </HTTP>
393    </DCPType>
394   </GetFeatureInfo>
395   <sld:GetLegendGraphic>
396    <Format>image/jpeg</Format>
397    <Format>image/png</Format>
398    <Format>application/json</Format>
399    <DCPType>
400     <HTTP>
401      <Get>
402       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
403      </Get>
404     </HTTP>
405    </DCPType>
406   </sld:GetLegendGraphic>
407   <sld:DescribeLayer>
408    <Format>text/xml</Format>
409    <DCPType>
410     <HTTP>
411      <Get>
412       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
413      </Get>
414     </HTTP>
415    </DCPType>
416   </sld:DescribeLayer>
417   <qgs:GetStyles>
418    <Format>text/xml</Format>
419    <DCPType>
420     <HTTP>
421      <Get>
422       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?"/>
423      </Get>
424     </HTTP>
425    </DCPType>
426   </qgs:GetStyles>
427  </Request>
428  <Exception>
429   <Format>XML</Format>
430  </Exception>
431  <sld:UserDefinedSymbolization RemoteWFS="0" SupportSLD="1" UserStyle="1" InlineFeature="0" RemoteWCS="0" UserLayer="0"/>
432  <Layer queryable="1">
433   <KeywordList>
434    <Keyword vocabulary="ISO">infoMapAccessService</Keyword>
435   </KeywordList>
436   <CRS>CRS:84</CRS>
437   <CRS>EPSG:3857</CRS>
438   <CRS>EPSG:4326</CRS>
439   <EX_GeographicBoundingBox>
440    <westBoundLongitude>-179.999926</westBoundLongitude>
441    <eastBoundLongitude>179.999927</eastBoundLongitude>
442    <southBoundLatitude>-89.999996</southBoundLatitude>
443    <northBoundLatitude>89.999996</northBoundLatitude>
444   </EX_GeographicBoundingBox>
445   <BoundingBox miny="-179.999926" maxy="179.999927" minx="-89.999996" maxx="89.999996" CRS="EPSG:4326"/>
446   <BoundingBox miny="-109516377.571" maxy="109516377.539" minx="-20037500.106" maxx="20037500.106" CRS="EPSG:3857"/>
447   <Layer queryable="1">
448    <Name>country-name</Name>
449    <Title>country-name</Title>
450    <CRS>CRS:84</CRS>
451    <CRS>EPSG:3857</CRS>
452    <CRS>EPSG:4326</CRS>
453    <EX_GeographicBoundingBox>
454     <westBoundLongitude>-177.228623</westBoundLongitude>
455     <eastBoundLongitude>178.519502</eastBoundLongitude>
456     <southBoundLatitude>-80.516517</southBoundLatitude>
457     <northBoundLatitude>73.348998</northBoundLatitude>
458    </EX_GeographicBoundingBox>
459    <BoundingBox miny="-177.228623" maxy="178.519502" minx="-80.516517" maxx="73.348998" CRS="EPSG:4326"/>
460    <BoundingBox miny="-15878600" maxy="12257700" minx="-19729000" maxx="19872700" CRS="EPSG:3857"/>
461    <Style>
462     <Name>default</Name>
463     <Title>default</Title>
464     <LegendURL>
465      <Format>image/png</Format>
466      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=country-name&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0"/>
467     </LegendURL>
468    </Style>
469   </Layer>
470   <Layer queryable="1">
471    <Name>state</Name>
472    <Title>state</Title>
473    <CRS>CRS:84</CRS>
474    <CRS>EPSG:3857</CRS>
475    <CRS>EPSG:4326</CRS>
476    <EX_GeographicBoundingBox>
477     <westBoundLongitude>-139.060207</westBoundLongitude>
478     <eastBoundLongitude>153.506568</eastBoundLongitude>
479     <southBoundLatitude>-39.201702</southBoundLatitude>
480     <northBoundLatitude>78.686917</northBoundLatitude>
481    </EX_GeographicBoundingBox>
482    <BoundingBox miny="-139.060207" maxy="153.506568" minx="-39.201702" maxx="78.686917" CRS="EPSG:4326"/>
483    <BoundingBox miny="-4750604.908" maxy="14747260.316" minx="-15480111.391" maxx="17088272.979" CRS="EPSG:3857"/>
484    <Style>
485     <Name>default</Name>
486     <Title>default</Title>
487     <LegendURL>
488      <Format>image/png</Format>
489      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=state&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0"/>
490     </LegendURL>
491    </Style>
492   </Layer>
493   <Layer queryable="1">
494    <Name>country</Name>
495    <Title>country</Title>
496    <CRS>CRS:84</CRS>
497    <CRS>EPSG:3857</CRS>
498    <CRS>EPSG:4326</CRS>
499    <EX_GeographicBoundingBox>
500     <westBoundLongitude>-179.999926</westBoundLongitude>
501     <eastBoundLongitude>179.999926</eastBoundLongitude>
502     <southBoundLatitude>-89.501388</southBoundLatitude>
503     <northBoundLatitude>83.634081</northBoundLatitude>
504    </EX_GeographicBoundingBox>
505    <BoundingBox miny="-179.999926" maxy="179.999926" minx="-89.501388" maxx="83.634081" CRS="EPSG:4326"/>
506    <BoundingBox miny="-34679800" maxy="18428900" minx="-20037500" maxx="20037500" CRS="EPSG:3857"/>
507    <Style>
508     <Name>default</Name>
509     <Title>default</Title>
510     <LegendURL>
511      <Format>image/png</Format>
512      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=country&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0"/>
513     </LegendURL>
514    </Style>
515   </Layer>
516   <Layer queryable="1">
517    <Name>geo-lines</Name>
518    <Title>geo-lines</Title>
519    <CRS>CRS:84</CRS>
520    <CRS>EPSG:3857</CRS>
521    <CRS>EPSG:4326</CRS>
522    <EX_GeographicBoundingBox>
523     <westBoundLongitude>-179.999926</westBoundLongitude>
524     <eastBoundLongitude>179.999926</eastBoundLongitude>
525     <southBoundLatitude>-89.999996</southBoundLatitude>
526     <northBoundLatitude>89.999996</northBoundLatitude>
527    </EX_GeographicBoundingBox>
528    <BoundingBox miny="-179.999926" maxy="179.999926" minx="-89.999996" maxx="89.999996" CRS="EPSG:4326"/>
529    <BoundingBox miny="-109516377.571" maxy="109516377.539" minx="-20037500.106" maxx="20037500.106" CRS="EPSG:3857"/>
530    <Layer queryable="1">
531     <Name>ne_10m_geographic_lines</Name>
532     <Title>ne_10m_geographic_lines</Title>
533     <CRS>CRS:84</CRS>
534     <CRS>EPSG:3857</CRS>
535     <CRS>EPSG:4326</CRS>
536     <EX_GeographicBoundingBox>
537      <westBoundLongitude>-179.999926</westBoundLongitude>
538      <eastBoundLongitude>179.999926</eastBoundLongitude>
539      <southBoundLatitude>-89.999996</southBoundLatitude>
540      <northBoundLatitude>89.999996</northBoundLatitude>
541     </EX_GeographicBoundingBox>
542     <BoundingBox miny="-179.999926" maxy="179.999926" minx="-89.999996" maxx="89.999996" CRS="EPSG:4326"/>
543     <BoundingBox miny="-108777000" maxy="108777000" minx="-20037500" maxx="20037500" CRS="EPSG:3857"/>
544     <Style>
545      <Name>default</Name>
546      <Title>default</Title>
547      <LegendURL>
548       <Format>image/png</Format>
549       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=ne_10m_geographic_lines&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0"/>
550      </LegendURL>
551     </Style>
552     <MinScaleDenominator>0</MinScaleDenominator>
553     <MaxScaleDenominator>5e+06</MaxScaleDenominator>
554    </Layer>
555    <Layer queryable="1">
556     <Name>ne_50m_geographic_lines</Name>
557     <Title>ne_50m_geographic_lines</Title>
558     <CRS>CRS:84</CRS>
559     <CRS>EPSG:3857</CRS>
560     <CRS>EPSG:4326</CRS>
561     <EX_GeographicBoundingBox>
562      <westBoundLongitude>-179.999926</westBoundLongitude>
563      <eastBoundLongitude>179.999926</eastBoundLongitude>
564      <southBoundLatitude>-89.999996</southBoundLatitude>
565      <northBoundLatitude>89.999996</northBoundLatitude>
566     </EX_GeographicBoundingBox>
567     <BoundingBox miny="-179.999926" maxy="179.999926" minx="-89.999996" maxx="89.999996" CRS="EPSG:4326"/>
568     <BoundingBox miny="-108777000" maxy="108777000" minx="-20037500" maxx="20037500" CRS="EPSG:3857"/>
569     <Style>
570      <Name>default</Name>
571      <Title>default</Title>
572      <LegendURL>
573       <Format>image/png</Format>
574       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:type="simple" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=ne_50m_geographic_lines&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0"/>
575      </LegendURL>
576     </Style>
577     <MinScaleDenominator>5e+06</MinScaleDenominator>
578     <MaxScaleDenominator>1e+08</MaxScaleDenominator>
579    </Layer>
580   </Layer>
581  </Layer>
582 </Capability>
583</WMS_Capabilities>
584    "#;
585        let cap: WmsCapabilities = from_reader(s.as_bytes()).unwrap();
586        println!("{:#?}", cap);
587
588        assert_eq!(cap.version, "1.3.0");
589        assert_eq!(cap.service.name, "WMS");
590        assert_eq!(cap.service.title, "untitled");
591        assert_eq!(
592            cap.service.keyword_list.as_ref().unwrap().keywords,
593            vec!["infoMapAccessService".to_string()]
594        );
595
596        assert_eq!(cap.capability.layers[0].name, None);
597        assert_eq!(cap.capability.layers[0].title, None);
598        assert_eq!(cap.capability.layers[0].queryable, Some(true));
599        assert_eq!(cap.capability.layers[0].abstract_, None);
600        assert_eq!(
601            cap.capability.layers[0].crs,
602            vec!["CRS:84", "EPSG:3857", "EPSG:4326"]
603        );
604        let bbox = cap.capability.layers[0]
605            .ex_geographic_bounding_box
606            .as_ref()
607            .unwrap();
608        assert_eq!(bbox.east_bound_longitude, 179.999927);
609        assert_eq!(bbox.south_bound_latitude, -89.999996);
610        assert_eq!(bbox.west_bound_longitude, -179.999926);
611        assert_eq!(bbox.north_bound_latitude, 89.999996);
612
613        assert_eq!(
614            cap.capability.layers[0].layers[0].name,
615            Some("country-name".to_string())
616        );
617        assert_eq!(
618            cap.capability.layers[0].layers[0].title,
619            Some("country-name".to_string())
620        );
621        assert_eq!(
622            cap.capability.layers[0].layers[0].crs,
623            vec!["CRS:84", "EPSG:3857", "EPSG:4326"]
624        );
625
626        assert_eq!(
627            cap.capability.layers[0].layers[3].layers[0].name,
628            Some("ne_10m_geographic_lines".to_string())
629        );
630        assert_eq!(
631            cap.capability.layers[0].layers[3].layers[0].min_scale_denominator,
632            Some(0.0)
633        );
634        assert_eq!(
635            cap.capability.layers[0].layers[3].layers[0].max_scale_denominator,
636            Some(5000000.0)
637        );
638    }
639
640    #[test]
641    fn qgis_getprojectsettings() {
642        let s = r#"<?xml version="1.0" encoding="utf-8"?>
643<WMS_Capabilities xsi:schemaLocation="http://www.opengis.net/wms http://schemas.opengis.net/wms/1.3.0/capabilities_1_3_0.xsd http://www.opengis.net/sld http://schemas.opengis.net/sld/1.1.0/sld_capabilities.xsd http://www.qgis.org/wms http://127.0.0.1:8080/wms/qgs/ne?SERVICE=WMS&amp;REQUEST=GetSchemaExtension" xmlns="http://www.opengis.net/wms" xmlns:sld="http://www.opengis.net/sld" version="1.3.0" xmlns:qgs="http://www.qgis.org/wms" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
644 <Service>
645  <Name>WMS</Name>
646  <Title>untitled</Title>
647  <KeywordList>
648   <Keyword vocabulary="ISO">infoMapAccessService</Keyword>
649  </KeywordList>
650  <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne" xlink:type="simple"/>
651  <Fees>conditions unknown</Fees>
652  <AccessConstraints>None</AccessConstraints>
653 </Service>
654 <Capability>
655  <Request>
656   <GetCapabilities>
657    <Format>text/xml</Format>
658    <DCPType>
659     <HTTP>
660      <Get>
661       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
662      </Get>
663     </HTTP>
664    </DCPType>
665   </GetCapabilities>
666   <GetMap>
667    <Format>image/jpeg</Format>
668    <Format>image/png</Format>
669    <Format>image/png; mode=16bit</Format>
670    <Format>image/png; mode=8bit</Format>
671    <Format>image/png; mode=1bit</Format>
672    <Format>application/dxf</Format>
673    <DCPType>
674     <HTTP>
675      <Get>
676       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
677      </Get>
678     </HTTP>
679    </DCPType>
680   </GetMap>
681   <GetFeatureInfo>
682    <Format>text/plain</Format>
683    <Format>text/html</Format>
684    <Format>text/xml</Format>
685    <Format>application/vnd.ogc.gml</Format>
686    <Format>application/vnd.ogc.gml/3.1.1</Format>
687    <Format>application/json</Format>
688    <Format>application/geo+json</Format>
689    <DCPType>
690     <HTTP>
691      <Get>
692       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
693      </Get>
694     </HTTP>
695    </DCPType>
696   </GetFeatureInfo>
697   <sld:GetLegendGraphic>
698    <Format>image/jpeg</Format>
699    <Format>image/png</Format>
700    <Format>application/json</Format>
701    <DCPType>
702     <HTTP>
703      <Get>
704       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
705      </Get>
706     </HTTP>
707    </DCPType>
708   </sld:GetLegendGraphic>
709   <sld:DescribeLayer>
710    <Format>text/xml</Format>
711    <DCPType>
712     <HTTP>
713      <Get>
714       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
715      </Get>
716     </HTTP>
717    </DCPType>
718   </sld:DescribeLayer>
719   <qgs:GetStyles>
720    <Format>text/xml</Format>
721    <DCPType>
722     <HTTP>
723      <Get>
724       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
725      </Get>
726     </HTTP>
727    </DCPType>
728   </qgs:GetStyles>
729   <GetPrint>
730    <Format>svg</Format>
731    <Format>png</Format>
732    <Format>pdf</Format>
733    <DCPType>
734     <HTTP>
735      <Get>
736       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?" xlink:type="simple"/>
737      </Get>
738     </HTTP>
739    </DCPType>
740   </GetPrint>
741  </Request>
742  <Exception>
743   <Format>XML</Format>
744  </Exception>
745  <sld:UserDefinedSymbolization RemoteWFS="0" UserStyle="1" SupportSLD="1" UserLayer="0" RemoteWCS="0" InlineFeature="0"/>
746  <WFSLayers>
747   <WFSLayer name="country"/>
748   <WFSLayer name="state"/>
749  </WFSLayers>
750  <Layer queryable="1">
751   <KeywordList>
752    <Keyword vocabulary="ISO">infoMapAccessService</Keyword>
753   </KeywordList>
754   <CRS>CRS:84</CRS>
755   <CRS>EPSG:3857</CRS>
756   <CRS>EPSG:4326</CRS>
757   <EX_GeographicBoundingBox>
758    <westBoundLongitude>-179.999926</westBoundLongitude>
759    <eastBoundLongitude>179.999927</eastBoundLongitude>
760    <southBoundLatitude>-89.999996</southBoundLatitude>
761    <northBoundLatitude>89.999996</northBoundLatitude>
762   </EX_GeographicBoundingBox>
763   <BoundingBox maxy="179.999927" miny="-179.999926" CRS="EPSG:4326" maxx="89.999996" minx="-89.999996"/>
764   <BoundingBox maxy="109516377.539" miny="-109516377.571" CRS="EPSG:3857" maxx="20037500.106" minx="-20037500.106"/>
765   <TreeName></TreeName>
766   <Layer geometryType="Point" queryable="1" opacity="1" visible="1" expanded="1" displayField="z_name">
767    <Name>ne</Name>
768    <Title>Natural Earth</Title>
769    <KeywordList>
770     <Keyword>countries</Keyword>
771     <Keyword>political</Keyword>
772    </KeywordList>
773    <CRS>CRS:84</CRS>
774    <CRS>EPSG:3857</CRS>
775    <CRS>EPSG:4326</CRS>
776    <EX_GeographicBoundingBox>
777     <westBoundLongitude>-177.228623</westBoundLongitude>
778     <eastBoundLongitude>178.519502</eastBoundLongitude>
779     <southBoundLatitude>-80.516517</southBoundLatitude>
780     <northBoundLatitude>73.348998</northBoundLatitude>
781    </EX_GeographicBoundingBox>
782    <BoundingBox maxy="178.519502" miny="-177.228623" CRS="EPSG:4326" maxx="73.348998" minx="-80.516517"/>
783    <BoundingBox maxy="12257700" miny="-15878600" CRS="EPSG:3857" maxx="19872700" minx="-19729000"/>
784    <Style>
785     <Name>default</Name>
786     <Title>default</Title>
787     <LegendURL>
788      <Format>image/png</Format>
789      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=ne&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0" xlink:type="simple"/>
790     </LegendURL>
791    </Style>
792    <DataURL>
793     <Format>text/plain</Format>
794     <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="https://www.naturalearthdata.com/" xlink:type="simple"/>
795    </DataURL>
796    <Attribution>
797     <Title>Natural Earth</Title>
798     <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="https://www.naturalearthdata.com/" xlink:type="simple"/>
799    </Attribution>
800    <MetadataURL type="">
801     <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="https://www.naturalearthdata.com/about/" xlink:type="simple"/>
802    </MetadataURL>
803    <TreeName>country-name</TreeName>
804    <PrimaryKey>
805     <PrimaryKeyAttribute>ogc_fid</PrimaryKeyAttribute>
806    </PrimaryKey>
807    <Attributes>
808     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ogc_fid"/>
809     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="scalerank"/>
810     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="labelrank"/>
811     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="z_postal"/>
812     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="z_abbrev"/>
813     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="z_name"/>
814     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="z_admin"/>
815     <Attribute length="30" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="featurecla"/>
816     <Attribute length="32" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="sovereignt"/>
817     <Attribute length="3" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="sov_a3"/>
818     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="adm0_dif"/>
819     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="level"/>
820     <Attribute length="17" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="type"/>
821     <Attribute length="36" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="admin"/>
822     <Attribute length="3" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_a3"/>
823     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="geou_dif"/>
824     <Attribute length="26" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name"/>
825     <Attribute length="13" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="abbrev"/>
826     <Attribute length="4" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="postal"/>
827     <Attribute length="53" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_forma"/>
828     <Attribute length="32" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="terr_"/>
829     <Attribute length="43" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_sort"/>
830     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="map_color"/>
831     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="pop_est"/>
832     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="gdp_md_est"/>
833     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="fips_10_"/>
834     <Attribute length="3" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_a2"/>
835     <Attribute length="3" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_a3"/>
836     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="iso_n3"/>
837    </Attributes>
838   </Layer>
839   <Layer geometryType="MultiLineString" queryable="1" opacity="1" visible="1" expanded="1" displayField="name">
840    <Name>state</Name>
841    <Title>state</Title>
842    <CRS>CRS:84</CRS>
843    <CRS>EPSG:3857</CRS>
844    <CRS>EPSG:4326</CRS>
845    <EX_GeographicBoundingBox>
846     <westBoundLongitude>-139.060207</westBoundLongitude>
847     <eastBoundLongitude>153.506568</eastBoundLongitude>
848     <southBoundLatitude>-39.201702</southBoundLatitude>
849     <northBoundLatitude>78.686917</northBoundLatitude>
850    </EX_GeographicBoundingBox>
851    <BoundingBox maxy="153.506568" miny="-139.060207" CRS="EPSG:4326" maxx="78.686917" minx="-39.201702"/>
852    <BoundingBox maxy="14747260.316" miny="-4750604.908" CRS="EPSG:3857" maxx="17088272.979" minx="-15480111.391"/>
853    <Style>
854     <Name>default</Name>
855     <Title>default</Title>
856     <LegendURL>
857      <Format>image/png</Format>
858      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=state&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0" xlink:type="simple"/>
859     </LegendURL>
860    </Style>
861    <TreeName>state</TreeName>
862    <PrimaryKey>
863     <PrimaryKeyAttribute>ogc_fid</PrimaryKeyAttribute>
864    </PrimaryKey>
865    <Attributes>
866     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ogc_fid"/>
867     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="featurecla"/>
868     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name"/>
869     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_a3"/>
870     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_name"/>
871     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="shape_leng"/>
872     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor13"/>
873     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor9"/>
874     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="sov_a3"/>
875     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_l"/>
876     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_r"/>
877     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_alt_l"/>
878     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_alt_r"/>
879     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_loc_l"/>
880     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_loc_r"/>
881     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="name_len_l"/>
882     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="name_len_r"/>
883     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="note"/>
884     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="type"/>
885     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="min_zoom"/>
886     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="min_label"/>
887     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="scalerank"/>
888    </Attributes>
889   </Layer>
890   <Layer geometryType="MultiPolygon" queryable="1" opacity="1" visible="1" expanded="0" displayField="name">
891    <Name>country</Name>
892    <Title>country</Title>
893    <CRS>CRS:84</CRS>
894    <CRS>EPSG:3857</CRS>
895    <CRS>EPSG:4326</CRS>
896    <EX_GeographicBoundingBox>
897     <westBoundLongitude>-179.999926</westBoundLongitude>
898     <eastBoundLongitude>179.999926</eastBoundLongitude>
899     <southBoundLatitude>-89.501388</southBoundLatitude>
900     <northBoundLatitude>83.634081</northBoundLatitude>
901    </EX_GeographicBoundingBox>
902    <BoundingBox maxy="179.999926" miny="-179.999926" CRS="EPSG:4326" maxx="83.634081" minx="-89.501388"/>
903    <BoundingBox maxy="18428900" miny="-34679800" CRS="EPSG:3857" maxx="20037500" minx="-20037500"/>
904    <Style>
905     <Name>default</Name>
906     <Title>default</Title>
907     <LegendURL>
908      <Format>image/png</Format>
909      <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=country&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0" xlink:type="simple"/>
910     </LegendURL>
911    </Style>
912    <TreeName>country</TreeName>
913    <PrimaryKey>
914     <PrimaryKeyAttribute>ogc_fid</PrimaryKeyAttribute>
915    </PrimaryKey>
916    <Attributes>
917     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ogc_fid"/>
918     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="featurecla"/>
919     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="scalerank"/>
920     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="labelrank"/>
921     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="sovereignt"/>
922     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="sov_a3"/>
923     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="adm0_dif"/>
924     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="level"/>
925     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="type"/>
926     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="admin"/>
927     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_a3"/>
928     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="geou_dif"/>
929     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="geounit"/>
930     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="gu_a3"/>
931     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="su_dif"/>
932     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="subunit"/>
933     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="su_a3"/>
934     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="brk_diff"/>
935     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name"/>
936     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_long"/>
937     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="brk_a3"/>
938     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="brk_name"/>
939     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="brk_group"/>
940     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="abbrev"/>
941     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="postal"/>
942     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="formal_en"/>
943     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="formal_fr"/>
944     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ciawf"/>
945     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="note_adm0"/>
946     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="note_brk"/>
947     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_sort"/>
948     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_alt"/>
949     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor7"/>
950     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor8"/>
951     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor9"/>
952     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="mapcolor13"/>
953     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="pop_est"/>
954     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="pop_rank"/>
955     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="gdp_md_est"/>
956     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="pop_year"/>
957     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="lastcensus"/>
958     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="gdp_year"/>
959     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="economy"/>
960     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="income_grp"/>
961     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="wikipedia"/>
962     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="fips_10_"/>
963     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_a2"/>
964     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_a3"/>
965     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_a3_eh"/>
966     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="iso_n3"/>
967     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="un_a3"/>
968     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="wb_a2"/>
969     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="wb_a3"/>
970     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="woe_id"/>
971     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="woe_id_eh"/>
972     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="woe_note"/>
973     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_a3_is"/>
974     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="adm0_a3_us"/>
975     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="adm0_a3_un"/>
976     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="adm0_a3_wb"/>
977     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="continent"/>
978     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="region_un"/>
979     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="subregion"/>
980     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="region_wb"/>
981     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="name_len"/>
982     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="long_len"/>
983     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="abbrev_len"/>
984     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="tiny"/>
985     <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="homepart"/>
986     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="min_zoom"/>
987     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="min_label"/>
988     <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="max_label"/>
989     <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ne_id"/>
990     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="wikidataid"/>
991     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ar"/>
992     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_bn"/>
993     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_de"/>
994     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_en"/>
995     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_es"/>
996     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_fr"/>
997     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_el"/>
998     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_hi"/>
999     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_hu"/>
1000     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_id"/>
1001     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_it"/>
1002     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ja"/>
1003     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ko"/>
1004     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_nl"/>
1005     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_pl"/>
1006     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_pt"/>
1007     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ru"/>
1008     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_sv"/>
1009     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_tr"/>
1010     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_vi"/>
1011     <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_zh"/>
1012    </Attributes>
1013   </Layer>
1014   <Layer queryable="1" visible="0" expanded="1" mutuallyExclusive="0">
1015    <Name>geo-lines</Name>
1016    <Title>geo-lines</Title>
1017    <CRS>CRS:84</CRS>
1018    <CRS>EPSG:3857</CRS>
1019    <CRS>EPSG:4326</CRS>
1020    <EX_GeographicBoundingBox>
1021     <westBoundLongitude>-179.999926</westBoundLongitude>
1022     <eastBoundLongitude>179.999926</eastBoundLongitude>
1023     <southBoundLatitude>-89.999996</southBoundLatitude>
1024     <northBoundLatitude>89.999996</northBoundLatitude>
1025    </EX_GeographicBoundingBox>
1026    <BoundingBox maxy="179.999926" miny="-179.999926" CRS="EPSG:4326" maxx="89.999996" minx="-89.999996"/>
1027    <BoundingBox maxy="109516377.539" miny="-109516377.571" CRS="EPSG:3857" maxx="20037500.106" minx="-20037500.106"/>
1028    <TreeName>geo-lines</TreeName>
1029    <Layer geometryType="MultiLineString" queryable="1" opacity="1" visible="0" expanded="1" displayField="name">
1030     <Name>ne_10m_geographic_lines</Name>
1031     <Title>ne_10m_geographic_lines</Title>
1032     <CRS>CRS:84</CRS>
1033     <CRS>EPSG:3857</CRS>
1034     <CRS>EPSG:4326</CRS>
1035     <EX_GeographicBoundingBox>
1036      <westBoundLongitude>-179.999926</westBoundLongitude>
1037      <eastBoundLongitude>179.999926</eastBoundLongitude>
1038      <southBoundLatitude>-89.999996</southBoundLatitude>
1039      <northBoundLatitude>89.999996</northBoundLatitude>
1040     </EX_GeographicBoundingBox>
1041     <BoundingBox maxy="179.999926" miny="-179.999926" CRS="EPSG:4326" maxx="89.999996" minx="-89.999996"/>
1042     <BoundingBox maxy="108777000" miny="-108777000" CRS="EPSG:3857" maxx="20037500" minx="-20037500"/>
1043     <Style>
1044      <Name>default</Name>
1045      <Title>default</Title>
1046      <LegendURL>
1047       <Format>image/png</Format>
1048       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=ne_10m_geographic_lines&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0" xlink:type="simple"/>
1049      </LegendURL>
1050     </Style>
1051     <MinScaleDenominator>0</MinScaleDenominator>
1052     <MaxScaleDenominator>5e+06</MaxScaleDenominator>
1053     <TreeName>ne_10m_geographic_lines</TreeName>
1054     <PrimaryKey>
1055      <PrimaryKeyAttribute>ogc_fid</PrimaryKeyAttribute>
1056     </PrimaryKey>
1057     <Attributes>
1058      <Attribute length="0" editType="" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ogc_fid"/>
1059      <Attribute length="0" editType="" type="qlonglong" comment="" precision="0" typeName="Integer64" name="scalerank"/>
1060      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name"/>
1061      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_long"/>
1062      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="abbrev"/>
1063      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="note"/>
1064      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="featurecla"/>
1065      <Attribute length="0" editType="" type="double" comment="" precision="0" typeName="Real" name="min_zoom"/>
1066      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="wikidataid"/>
1067      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_ar"/>
1068      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_bn"/>
1069      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_de"/>
1070      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_en"/>
1071      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_es"/>
1072      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_fr"/>
1073      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_el"/>
1074      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_hi"/>
1075      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_hu"/>
1076      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_id"/>
1077      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_it"/>
1078      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_ja"/>
1079      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_ko"/>
1080      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_nl"/>
1081      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_pl"/>
1082      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_pt"/>
1083      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_ru"/>
1084      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_sv"/>
1085      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_tr"/>
1086      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_vi"/>
1087      <Attribute length="0" editType="" type="QString" comment="" precision="0" typeName="String" name="name_zh"/>
1088      <Attribute length="0" editType="" type="int" comment="" precision="0" typeName="Integer" name="wdid_score"/>
1089      <Attribute length="0" editType="" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ne_id"/>
1090     </Attributes>
1091    </Layer>
1092    <Layer geometryType="MultiLineString" queryable="1" opacity="1" visible="0" expanded="1" displayField="name">
1093     <Name>ne_50m_geographic_lines</Name>
1094     <Title>ne_50m_geographic_lines</Title>
1095     <CRS>CRS:84</CRS>
1096     <CRS>EPSG:3857</CRS>
1097     <CRS>EPSG:4326</CRS>
1098     <EX_GeographicBoundingBox>
1099      <westBoundLongitude>-179.999926</westBoundLongitude>
1100      <eastBoundLongitude>179.999926</eastBoundLongitude>
1101      <southBoundLatitude>-89.999996</southBoundLatitude>
1102      <northBoundLatitude>89.999996</northBoundLatitude>
1103     </EX_GeographicBoundingBox>
1104     <BoundingBox maxy="179.999926" miny="-179.999926" CRS="EPSG:4326" maxx="89.999996" minx="-89.999996"/>
1105     <BoundingBox maxy="108777000" miny="-108777000" CRS="EPSG:3857" maxx="20037500" minx="-20037500"/>
1106     <Style>
1107      <Name>default</Name>
1108      <Title>default</Title>
1109      <LegendURL>
1110       <Format>image/png</Format>
1111       <OnlineResource xmlns:xlink="http://www.w3.org/1999/xlink" xlink:href="http://127.0.0.1:8080/wms/qgs/ne?&amp;SERVICE=WMS&amp;VERSION=1.3.0&amp;REQUEST=GetLegendGraphic&amp;LAYER=ne_50m_geographic_lines&amp;FORMAT=image/png&amp;STYLE=default&amp;SLD_VERSION=1.1.0" xlink:type="simple"/>
1112      </LegendURL>
1113     </Style>
1114     <MinScaleDenominator>5e+06</MinScaleDenominator>
1115     <MaxScaleDenominator>1e+08</MaxScaleDenominator>
1116     <TreeName>ne_50m_geographic_lines</TreeName>
1117     <PrimaryKey>
1118      <PrimaryKeyAttribute>ogc_fid</PrimaryKeyAttribute>
1119     </PrimaryKey>
1120     <Attributes>
1121      <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ogc_fid"/>
1122      <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="scalerank"/>
1123      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name"/>
1124      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_long"/>
1125      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="abbrev"/>
1126      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="note"/>
1127      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="featurecla"/>
1128      <Attribute length="0" editType="TextEdit" type="double" comment="" precision="0" typeName="Real" name="min_zoom"/>
1129      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="wikidataid"/>
1130      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ar"/>
1131      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_bn"/>
1132      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_de"/>
1133      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_en"/>
1134      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_es"/>
1135      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_fr"/>
1136      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_el"/>
1137      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_hi"/>
1138      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_hu"/>
1139      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_id"/>
1140      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_it"/>
1141      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ja"/>
1142      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ko"/>
1143      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_nl"/>
1144      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_pl"/>
1145      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_pt"/>
1146      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_ru"/>
1147      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_sv"/>
1148      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_tr"/>
1149      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_vi"/>
1150      <Attribute length="0" editType="TextEdit" type="QString" comment="" precision="0" typeName="String" name="name_zh"/>
1151      <Attribute length="0" editType="Range" type="int" comment="" precision="0" typeName="Integer" name="wdid_score"/>
1152      <Attribute length="0" editType="TextEdit" type="qlonglong" comment="" precision="0" typeName="Integer64" name="ne_id"/>
1153     </Attributes>
1154    </Layer>
1155   </Layer>
1156  </Layer>
1157  <LayerDrawingOrder>ne_50m_geographic_lines,ne_10m_geographic_lines,country,state,ne</LayerDrawingOrder>
1158 </Capability>
1159</WMS_Capabilities>
1160    "#;
1161        let cap: WmsCapabilities = from_reader(s.as_bytes()).unwrap();
1162        println!("{:#?}", cap);
1163
1164        assert_eq!(cap.version, "1.3.0");
1165        assert_eq!(cap.service.name, "WMS");
1166        assert_eq!(cap.service.title, "untitled");
1167
1168        assert_eq!(cap.capability.layers[0].name, None);
1169        assert_eq!(cap.capability.layers[0].title, None);
1170        assert_eq!(cap.capability.layers[0].queryable, Some(true));
1171        assert_eq!(cap.capability.layers[0].abstract_, None);
1172        assert_eq!(
1173            cap.capability.layers[0].crs,
1174            vec!["CRS:84", "EPSG:3857", "EPSG:4326"]
1175        );
1176
1177        let layer = &cap.capability.layers[0].layers[0];
1178        assert_eq!(layer.name, Some("ne".to_string()));
1179        assert_eq!(layer.title, Some("Natural Earth".to_string()));
1180        assert_eq!(layer.crs, vec!["CRS:84", "EPSG:3857", "EPSG:4326"]);
1181        assert_eq!(layer.attribution.as_ref().unwrap().title, "Natural Earth");
1182        assert_eq!(
1183            layer.attribution.as_ref().unwrap().online_resource.href,
1184            "https://www.naturalearthdata.com/"
1185        );
1186        assert_eq!(
1187            layer.data_url.as_ref().unwrap().online_resource.href,
1188            "https://www.naturalearthdata.com/"
1189        );
1190
1191        // <Layer opacity="1" visible="1" queryable="1" displayField="z_name" geometryType="Point" expanded="1">
1192        assert_eq!(layer.opacity, Some(1.0));
1193        assert_eq!(layer.visible, Some(true));
1194        assert_eq!(layer.display_field, Some("z_name".to_string()));
1195        assert_eq!(layer.geometry_type, Some("Point".to_string()));
1196        assert_eq!(layer.expanded, Some(true));
1197
1198        let layer = &cap.capability.layers[0].layers[3];
1199        assert_eq!(layer.name, Some("geo-lines".to_string()));
1200        // <Layer visible="0" queryable="1" expanded="1" mutuallyExclusive="0">
1201        assert_eq!(layer.mutually_exclusive, Some(false));
1202    }
1203}