Statistics
| Revision:

svn-gvsig-desktop / trunk / libraries / libRemoteServices / src / org / gvsig / remoteClient / wms / wms_1_3_0 / WMSProtocolHandler1_3_0.java @ 14705

History | View | Annotate | Download (16.2 KB)

1 3660 ldiaz
2
package org.gvsig.remoteClient.wms.wms_1_3_0;
3
4
import java.io.ByteArrayInputStream;
5
import java.io.File;
6
import java.io.IOException;
7
import java.util.ArrayList;
8
import java.util.TreeMap;
9 4926 jaume
10 3660 ldiaz
import org.gvsig.remoteClient.utils.CapabilitiesTags;
11 14705 jpiera
import org.gvsig.remoteClient.utils.EncodingXMLParser;
12 3660 ldiaz
import org.gvsig.remoteClient.utils.ExceptionTags;
13 9368 ldiaz
import org.gvsig.remoteClient.utils.Utilities;
14
import org.gvsig.remoteClient.wms.WMSStatus;
15 3660 ldiaz
import org.kxml2.io.KXmlParser;
16
import org.xmlpull.v1.XmlPullParserException;
17
18
/**
19
 * <p>
20
 * Describes the handler to comunicate to a WMS 1.3.0
21
 * </p>
22
 */
23
public class WMSProtocolHandler1_3_0 extends org.gvsig.remoteClient.wms.WMSProtocolHandler {
24
        private WMSLayer1_3_0 fakeRootLayer;
25
26
        public WMSProtocolHandler1_3_0()
27
        {
28
                this.version = "1.3.0";
29
                this.name = "WMS1.3.0";
30
                this.serviceInfo = new ServiceInformation();
31 4222 jaume
                this.layers = new TreeMap();
32 3660 ldiaz
        }
33
34
//------------------------------------------------------------------------------
35
// Parsing methods....
36
//------------------------------------------------------------------------------
37
/**
38
 * <p>Parse the xml data retrieved from the WMS, it will parse the WMS Capabilities</p>
39
 *
40
 */
41
    public void parse(File f)
42 5539 jaume
    {
43
            rootLayer = null;
44 3660 ldiaz
45
            int tag;
46 14705 jpiera
              EncodingXMLParser kxmlParser = null;
47
            kxmlParser = new EncodingXMLParser();
48 3660 ldiaz
            try
49
            {
50 14705 jpiera
                       kxmlParser.setInput(f);
51 3660 ldiaz
                        kxmlParser.nextTag();
52
                    if ( kxmlParser.getEventType() != KXmlParser.END_DOCUMENT )
53
                    {
54 3687 ldiaz
                            kxmlParser.require(KXmlParser.START_TAG, null, CapabilitiesTags.CAPABILITIES_ROOT1_3_0);
55 3660 ldiaz
                            tag = kxmlParser.nextTag();
56
                                 while(tag != KXmlParser.END_DOCUMENT)
57
                                 {
58
                     switch(tag)
59 4222 jaume
                                         {
60 3660 ldiaz
                                                case KXmlParser.START_TAG:
61
                                                        if (kxmlParser.getName().compareTo(CapabilitiesTags.SERVICE )==0)
62
                                                        {
63
                                                                parseServiceTag(kxmlParser);
64
                                                        }
65
                                                        else if (kxmlParser.getName().compareTo(CapabilitiesTags.CAPABILITY)==0)
66
                                                        {
67
                                                                parseCapabilityTag(kxmlParser);
68
                                                        }
69
                                                        break;
70
                                                case KXmlParser.END_TAG:
71
                                                        break;
72
                                                case KXmlParser.TEXT:
73 4222 jaume
                                                        //System.out.println("[TEXT]["+kxmlParser.getText()+"]");
74 3660 ldiaz
                                                break;
75
                                         }
76
                                     tag = kxmlParser.next();
77 3743 ldiaz
                             }//while !END_DOCUMENT
78 3660 ldiaz
                    }
79
            }
80 4222 jaume
            catch(XmlPullParserException parser_ex){
81 3660 ldiaz
                    parser_ex.printStackTrace();
82
            }
83
                   catch (IOException ioe) {
84
                           ioe.printStackTrace();
85 4222 jaume
                 } finally {
86 3660 ldiaz
87
        }
88
                   // In the parsing process the layer has been filled
89
    }
90
91
    /**
92
     * <p>Parses the Service Information </p>
93
     */
94
    private void parseServiceTag(KXmlParser parser) throws IOException, XmlPullParserException
95
    {
96
            int currentTag;
97
            boolean end = false;
98
99
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.SERVICE);
100
            currentTag = parser.next();
101
102
            while (!end)
103
            {
104
                         switch(currentTag)
105
                         {
106
                                case KXmlParser.START_TAG:
107
                                        if (parser.getName().compareTo(CapabilitiesTags.NAME)==0)
108
                                        {
109
                                                serviceInfo.name = parser.nextText();
110
                                        }
111
                                        else if (parser.getName().compareTo(CapabilitiesTags.TITLE)==0)
112
                                        {
113
                                                serviceInfo.title = parser.nextText();
114
                                        }
115
                                        else if (parser.getName().compareTo(CapabilitiesTags.ABSTRACT)==0)
116
                                        {
117
                                                serviceInfo.abstr = parser.nextText();
118
                                        }
119 4222 jaume
                                        else if (parser.getName().compareTo(CapabilitiesTags.ONLINERESOURCE)==0)
120
                                        {
121
                                            String value = new String();
122
                                        value = parser.getAttributeValue("", CapabilitiesTags.XLINK_HREF);
123
                                        if (value != null){
124
                                                serviceInfo.online_resource = value;
125
                                        }
126
                                        }
127 3660 ldiaz
                                        else if ((parser.getName().compareTo(CapabilitiesTags.KEYWORDLIST)==0) ||
128
                                                        (parser.getName().compareTo(CapabilitiesTags.CONTACTINFORMATION)==0))
129
                                        {
130
                                                parser.skipSubTree();
131
                                        }
132
                                        break;
133
                                case KXmlParser.END_TAG:
134
                                        if (parser.getName().compareTo(CapabilitiesTags.SERVICE) == 0)
135
                                                end = true;
136
                                        break;
137
                                case KXmlParser.TEXT:
138
                                break;
139
                         }
140
             if (!end)
141
                 currentTag = parser.next();
142
            }
143
            parser.require(KXmlParser.END_TAG, null, CapabilitiesTags.SERVICE);
144
    }
145 4222 jaume
146 3660 ldiaz
    /**
147
     * <p>Parses the Capability Tag </p>
148
     */
149
    private void parseCapabilityTag(KXmlParser parser) throws IOException, XmlPullParserException
150
    {
151
            int currentTag;
152
            boolean end = false;
153
154
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.CAPABILITY);
155
            currentTag = parser.next();
156
157
            while (!end)
158
            {
159
                         switch(currentTag)
160
                         {
161
                                case KXmlParser.START_TAG:
162
                                        if (parser.getName().compareTo(CapabilitiesTags.REQUEST)==0)
163
                                        {
164
                                                parseRequestTag(parser);
165
                                        }
166
                                        else if (parser.getName().compareTo(CapabilitiesTags.EXCEPTION)==0)
167
                                        {
168 4222 jaume
                                                //TODO:
169
                                                //Add to serviceInformation the supported exception formats.
170 3660 ldiaz
                                        }
171
                                        else if (parser.getName().compareTo(CapabilitiesTags.LAYER)==0)
172
                                        {
173
                                                WMSLayer1_3_0 lyr = new WMSLayer1_3_0();
174
                        if (rootLayer == null)
175
                            rootLayer = lyr;
176
                        else {
177
                            // Handles when there is no general root layer, will use
178
                            // a fake non-queryable one.
179
                            if (!rootLayer.equals(getFakeRootLayer())){
180
                                WMSLayer1_3_0 aux = (WMSLayer1_3_0) rootLayer;
181
                                rootLayer  = getFakeRootLayer();
182
                                rootLayer.getChildren().add(aux);
183
                            }
184
                            rootLayer.getChildren().add(lyr);
185
                        }
186
                                                lyr.parse(parser, layers);
187
188
                        if (lyr.getName()!=null)
189 4222 jaume
                                                    layers.put(lyr.getName(), lyr);
190 3660 ldiaz
                                        }
191
                                        else if ((parser.getName().compareTo(CapabilitiesTags.VENDORSPECIFICCAPABILITIES)==0) ||
192 4222 jaume
                                                        (parser.getName().compareTo(CapabilitiesTags.USERDEFINEDSYMBOLIZATION )==0))
193 3660 ldiaz
                                        {
194
                                                parser.skipSubTree();
195
                                        }
196
                                        break;
197
                                case KXmlParser.END_TAG:
198
                                        if (parser.getName().compareTo(CapabilitiesTags.CAPABILITY) == 0)
199
                                                end = true;
200
                                        break;
201
                                case KXmlParser.TEXT:
202
                                break;
203
                         }
204 4222 jaume
                         if (!end)
205
                                 currentTag = parser.next();
206 3660 ldiaz
            }
207
            //parser.require(KXmlParser.END_TAG, null, CapabilitiesTags.CAPABILITY);
208
    }
209
210
    /**
211
     * <p>Parses the Request tag </p>
212
     */
213
    private void parseRequestTag(KXmlParser parser) throws IOException, XmlPullParserException
214
    {
215
            int currentTag;
216
            boolean end = false;
217
218
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.REQUEST);
219
            currentTag = parser.next();
220
221
            while (!end)
222
            {
223
                         switch(currentTag)
224
                         {
225
                                case KXmlParser.START_TAG:
226
                                        if (parser.getName().compareTo(CapabilitiesTags.GETCAPABILITIES)==0)
227
                                        {
228 4222 jaume
                                                //we could parse here the info of Capabilities request, but we actually never use it.
229 3660 ldiaz
                                        }
230
                                        else if (parser.getName().compareTo(CapabilitiesTags.GETMAP)==0)
231 4222 jaume
                                        {
232
                                                serviceInfo.operations.put(CapabilitiesTags.GETMAP, null);
233
                                                parseGetMapTag(parser);
234 3660 ldiaz
                                        }
235
                                        else if (parser.getName().compareTo(CapabilitiesTags.GETFEATUREINFO)==0)
236
                                        {
237 4222 jaume
                                                serviceInfo.operations.put(CapabilitiesTags.GETFEATUREINFO, null);
238
                                                parseGetFeatureInfoTag(parser);
239 7946 ldiaz
                                        }
240
                                        else if (parser.getName().compareTo(CapabilitiesTags.DESCRIBELAYER)==0)
241
                                        {
242
                                                serviceInfo.operations.put(CapabilitiesTags.DESCRIBELAYER, null);
243
                                        }
244
                                        else if (parser.getName().compareTo(CapabilitiesTags.GETLEGENDGRAPHIC)==0)
245
                                        {
246
                                                serviceInfo.operations.put(CapabilitiesTags.GETLEGENDGRAPHIC, null);
247
                                                parseGetLegendGraphicTag(parser);
248
                                        }
249 3660 ldiaz
                                        break;
250
                                case KXmlParser.END_TAG:
251
                                        if (parser.getName().compareTo(CapabilitiesTags.REQUEST) == 0)
252
                                                end = true;
253
                                        break;
254
                                case KXmlParser.TEXT:
255
                                break;
256
                         }
257 4222 jaume
                         if (!end)
258
                                 currentTag = parser.next();
259 3660 ldiaz
            }
260
            // TODO: does not get such a tag when arrives here!!!!!!
261
            //parser.require(KXmlParser.END_TAG, null, CapabilitiesTags.REQUEST);
262
    }
263 4222 jaume
264
    /**
265
     * <p>Parses the GetMap tag </p>
266
     */
267
    private void parseGetMapTag(KXmlParser parser) throws IOException, XmlPullParserException
268
    {
269
            int currentTag;
270
            boolean end = false;
271
272
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.GETMAP);
273
            currentTag = parser.next();
274
275
            while (!end)
276
            {
277
                         switch(currentTag)
278
                         {
279
                                case KXmlParser.START_TAG:
280
                                        if (parser.getName().compareTo(CapabilitiesTags.FORMAT)==0)
281
                                        {
282
                                                serviceInfo.formats.add(parser.nextText());
283
                                        }
284
                                        else if (parser.getName().compareTo(CapabilitiesTags.DCPTYPE)==0)
285
                                        {
286
                                                currentTag = parser.nextTag();
287
                                                if(parser.getName().compareTo(CapabilitiesTags.HTTP)==0)
288
                                                {
289
                                                        currentTag = parser.nextTag();
290
                                                        if(parser.getName().compareTo(CapabilitiesTags.GET)==0)
291
                                                        {
292
                                                                currentTag = parser.nextTag();
293
                                                                if (parser.getName().compareTo(CapabilitiesTags.ONLINERESOURCE)==0)
294
                                                                {
295
                                                                        String value = new String();
296
                                                                        value = parser.getAttributeValue("", CapabilitiesTags.XLINK_HREF);
297
                                                                        if (value != null){
298
                                                                                serviceInfo.operations.put(CapabilitiesTags.GETMAP, value);
299
                                                                        }
300
                                                                }
301
                                                        }
302
                                                }
303
                                        }
304
                                        break;
305
                                case KXmlParser.END_TAG:
306
                                        if (parser.getName().compareTo(CapabilitiesTags.GETMAP) == 0)
307
                                                end = true;
308
                                        break;
309
                                case KXmlParser.TEXT:
310
                                break;
311
                         }
312
                         if(!end)
313
                                 currentTag = parser.next();
314
            }
315
    }
316
317
    /**
318 7946 ldiaz
     * <p>Parses the GetFeatureInfo tag </p>
319 4222 jaume
     */
320
    private void parseGetFeatureInfoTag(KXmlParser parser) throws IOException, XmlPullParserException
321
    {
322
            int currentTag;
323
            boolean end = false;
324
325
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.GETFEATUREINFO);
326
            currentTag = parser.next();
327
328
            while (!end)
329
            {
330
                         switch(currentTag)
331
                         {
332
                                case KXmlParser.START_TAG:
333
                                        if (parser.getName().compareTo(CapabilitiesTags.FORMAT)==0)
334
                                        {
335
                                                //TODO:
336
                                                // add the supported formats by the GetFeatureInfo request
337
                                                //serviceInfo.formats.add(parser.nextText());
338
                                        }
339
                                        else if (parser.getName().compareTo(CapabilitiesTags.DCPTYPE)==0)
340
                                        {
341
                                                currentTag = parser.nextTag();
342
                                                if(parser.getName().compareTo(CapabilitiesTags.HTTP)==0)
343
                                                {
344
                                                        currentTag = parser.nextTag();
345
                                                        if(parser.getName().compareTo(CapabilitiesTags.GET)==0)
346
                                                        {
347
                                                                currentTag = parser.nextTag();
348
                                                                if (parser.getName().compareTo(CapabilitiesTags.ONLINERESOURCE)==0)
349
                                                                {
350
                                                                        String value = new String();
351
                                                                        value = parser.getAttributeValue("", CapabilitiesTags.XLINK_HREF);
352
                                                                        if (value != null){
353 4623 ldiaz
                                                                                //serviceInfo.online_resource = value;
354
                                                                                serviceInfo.operations.put(CapabilitiesTags.GETFEATUREINFO, value);
355 4222 jaume
                                                                        }
356
                                                                }
357
                                                        }
358
                                                }
359
                                        }
360
                                        break;
361
                                case KXmlParser.END_TAG:
362
                                        if (parser.getName().compareTo(CapabilitiesTags.GETFEATUREINFO) == 0)
363
                                                end = true;
364
                                        break;
365
                                case KXmlParser.TEXT:
366
                                break;
367
                         }
368
                         if(!end)
369
                                 currentTag = parser.next();
370
            }
371
    }
372 3660 ldiaz
373 7946 ldiaz
    /**
374
     * <p>Parses the GetLegendGraphic tag </p>
375
     */
376
    private void parseGetLegendGraphicTag(KXmlParser parser) throws IOException, XmlPullParserException
377
    {
378
            int currentTag;
379
            boolean end = false;
380
381
            parser.require(KXmlParser.START_TAG, null, CapabilitiesTags.GETLEGENDGRAPHIC);
382
            currentTag = parser.next();
383
384
            while (!end)
385
            {
386
                         switch(currentTag)
387
                         {
388
                                case KXmlParser.START_TAG:
389
                                        if (parser.getName().compareTo(CapabilitiesTags.FORMAT)==0)
390
                                        {
391
                                                //TODO:
392
                                                // add the supported formats by the GetLegendGraphic request
393
                                                //serviceInfo.formats.add(parser.nextText());
394
                                        }
395
                                        else if (parser.getName().compareTo(CapabilitiesTags.DCPTYPE)==0)
396
                                        {
397
                                                currentTag = parser.nextTag();
398
                                                if(parser.getName().compareTo(CapabilitiesTags.HTTP)==0)
399
                                                {
400
                                                        currentTag = parser.nextTag();
401
                                                        if(parser.getName().compareTo(CapabilitiesTags.GET)==0)
402
                                                        {
403
                                                                currentTag = parser.nextTag();
404
                                                                if (parser.getName().compareTo(CapabilitiesTags.ONLINERESOURCE)==0)
405
                                                                {
406
                                                                        String value = new String();
407
                                                                        value = parser.getAttributeValue("", CapabilitiesTags.XLINK_HREF);
408
                                                                        if (value != null){
409
                                                                                serviceInfo.operations.put(CapabilitiesTags.GETLEGENDGRAPHIC, value);
410
                                                                        }
411
                                                                }
412
                                                        }
413
                                                }
414
                                        }
415
                                        break;
416
                                case KXmlParser.END_TAG:
417
                                        if (parser.getName().compareTo(CapabilitiesTags.GETLEGENDGRAPHIC) == 0)
418
                                                end = true;
419
                                        break;
420
                                case KXmlParser.TEXT:
421
                                break;
422
                         }
423
                         if(!end)
424
                                 currentTag = parser.next();
425
            }
426
    }
427
428 3660 ldiaz
    private WMSLayer1_3_0 getFakeRootLayer(){
429
        if (fakeRootLayer == null){
430
            fakeRootLayer = new WMSLayer1_3_0();
431
            fakeRootLayer.setTitle(serviceInfo.title);
432
            fakeRootLayer.setQueryable(false);
433
            fakeRootLayer.setName(null);
434
        }
435
        return fakeRootLayer;
436
    }
437
    /* (non-Javadoc)
438
     * @see org.gvsig.remoteClient.wms.WMSProtocolHandler#parseException(byte[])
439
     */
440
    protected String parseException(byte[] data) {
441
        ArrayList errors = new ArrayList();
442
        KXmlParser kxmlParser = new KXmlParser();
443
        try
444
        {
445 4500 jaume
            kxmlParser.setInput(new ByteArrayInputStream(data), encoding);
446 3660 ldiaz
            kxmlParser.nextTag();
447
            int tag;
448
            if ( kxmlParser.getEventType() != KXmlParser.END_DOCUMENT )
449
            {
450
                kxmlParser.require(KXmlParser.START_TAG, null, ExceptionTags.EXCEPTION_ROOT);
451
                tag = kxmlParser.nextTag();
452
                 while(tag != KXmlParser.END_DOCUMENT)
453
                 {
454
                     switch(tag)
455
                     {
456
                        case KXmlParser.START_TAG:
457
                            if (kxmlParser.getName().compareTo(ExceptionTags.SERVICE_EXCEPTION)==0){
458
                                String errorCode = kxmlParser.getAttributeValue("", ExceptionTags.CODE);
459
                                errorCode = (errorCode != null) ? "["+errorCode+"] " : "";
460
                                String errorMessage = kxmlParser.nextText();
461
                                errors.add(errorCode+errorMessage);
462
                            }
463
                            break;
464
                        case KXmlParser.END_TAG:
465
                            break;
466
467
                     }
468
                     tag = kxmlParser.nextTag();
469
                 }
470
                 //kxmlParser.require(KXmlParser.END_DOCUMENT, null, null);
471
            }
472
        }
473
        catch(XmlPullParserException parser_ex){
474
            System.out.println(parser_ex.getMessage());
475
            parser_ex.printStackTrace();
476
        }
477
        catch (IOException ioe) {
478
            ioe.printStackTrace();
479
        }
480
        String message = errors.size()>0? "" : null;
481
        for (int i = 0; i < errors.size(); i++) {
482
            message += (String) errors.get(i)+"\n";
483
        }
484
        return message;
485
    }
486 9368 ldiaz
487
    /**
488
     * Builds the GetFeatureInfoRequest according to the 1.3.0 OGC WMS Specifications
489
     */
490
    protected String buildGetFeatureInfoRequest(WMSStatus status, int x, int y)
491
    {
492
//            TODO: pass by parameter the info output format?
493
                StringBuffer req = new StringBuffer();
494
                String symbol = null;
495
496
                String onlineResource;
497
                if (status.getOnlineResource() == null)
498
                        onlineResource = getHost();
499
                else
500
                        onlineResource = status.getOnlineResource();
501
                symbol = getSymbol(onlineResource);
502
503
                req.append(onlineResource).append(symbol).append("REQUEST=GetFeatureInfo&SERVICE=WMS&");
504
                req.append("QUERY_LAYERS=").append(Utilities.Vector2CS(status.getLayerNames()));
505
                req.append("&VERSION=").append(getVersion()).append("&INFO_FORMAT=application/vnd.ogc.gml&");
506
                req.append(getPartialQuery(status)).append("&I="+x + "&J="+y);
507
                req.append("&FEATURE_COUNT=10000");
508
       if (status.getExceptionFormat() != null) {
509
            req.append("&EXCEPTIONS=" + status.getExceptionFormat());
510
        } else {
511
            req.append("&EXCEPTIONS=XML");
512
        }
513
                return req.toString().replaceAll(" ", "%20");
514
    }
515 3660 ldiaz
  }