Statistics
| Revision:

root / org.gvsig.wfs.app / trunk / org.gvsig.wfs.app / org.gvsig.wfs.app.mainplugin / src / main / java / org / gvsig / fmap / dal / store / wfs / WFSStoreProvider.java @ 416

History | View | Annotate | Download (22.7 KB)

1
/* gvSIG. Geographic Information System of the Valencian Government
2
 *
3
 * Copyright (C) 2007-2008 Infrastructures and Transports Department
4
 * of the Valencian Government (CIT)
5
 *
6
 * This program is free software; you can redistribute it and/or
7
 * modify it under the terms of the GNU General Public License
8
 * as published by the Free Software Foundation; either version 2
9
 * of the License, or (at your option) any later version.
10
 *
11
 * This program is distributed in the hope that it will be useful,
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
 * GNU General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU General Public License
17
 * along with this program; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19
 * MA  02110-1301, USA.
20
 *
21
 */
22

    
23
/*
24
 * AUTHORS (In addition to CIT):
25
 * 2009 {Iver T.I.}   {Task}
26
 */
27

    
28
package org.gvsig.fmap.dal.store.wfs;
29

    
30
import java.awt.geom.AffineTransform;
31
import java.io.File;
32
import java.io.IOException;
33
import java.util.ArrayList;
34
import java.util.Iterator;
35
import java.util.List;
36

    
37
import org.cresques.cts.ICoordTrans;
38
import org.cresques.cts.IProjection;
39
import org.gvsig.fmap.crs.CRSFactory;
40
import org.gvsig.fmap.dal.DALLocator;
41
import org.gvsig.fmap.dal.DataManager;
42
import org.gvsig.fmap.dal.DataServerExplorer;
43
import org.gvsig.fmap.dal.DataStoreParameters;
44
import org.gvsig.fmap.dal.DataTypes;
45
import org.gvsig.fmap.dal.exception.ConnectionServerException;
46
import org.gvsig.fmap.dal.exception.DataException;
47
import org.gvsig.fmap.dal.exception.InitializeException;
48
import org.gvsig.fmap.dal.exception.OpenException;
49
import org.gvsig.fmap.dal.exception.ProviderNotRegisteredException;
50
import org.gvsig.fmap.dal.exception.ReadException;
51
import org.gvsig.fmap.dal.feature.EditableFeatureAttributeDescriptor;
52
import org.gvsig.fmap.dal.feature.EditableFeatureType;
53
import org.gvsig.fmap.dal.feature.FeatureQuery;
54
import org.gvsig.fmap.dal.feature.FeatureStore;
55
import org.gvsig.fmap.dal.feature.FeatureType;
56
import org.gvsig.fmap.dal.feature.spi.AbstractFeatureStoreProvider;
57
import org.gvsig.fmap.dal.feature.spi.FeatureProvider;
58
import org.gvsig.fmap.dal.feature.spi.FeatureReferenceProviderServices;
59
import org.gvsig.fmap.dal.feature.spi.FeatureSetProvider;
60
import org.gvsig.fmap.dal.resource.spi.ResourceProvider;
61
import org.gvsig.fmap.dal.serverexplorer.wfs.WFSServerExplorer;
62
import org.gvsig.fmap.dal.serverexplorer.wfs.WFSServerExplorerParameters;
63
import org.gvsig.fmap.dal.spi.DataStoreProviderServices;
64
import org.gvsig.fmap.dal.store.gpe.GPEStoreProvider;
65
import org.gvsig.fmap.geom.Geometry;
66
import org.gvsig.fmap.geom.Geometry.SUBTYPES;
67
import org.gvsig.fmap.geom.GeometryLocator;
68
import org.gvsig.fmap.geom.GeometryManager;
69
import org.gvsig.fmap.geom.exception.CreateEnvelopeException;
70
import org.gvsig.fmap.geom.operation.GeometryOperationException;
71
import org.gvsig.fmap.geom.operation.GeometryOperationNotSupportedException;
72
import org.gvsig.fmap.geom.primitive.Envelope;
73
import org.gvsig.gpe.lib.api.exceptions.WriterHandlerCreationException;
74
import org.gvsig.metadata.MetadataLocator;
75
import org.gvsig.metadata.MetadataManager;
76
import org.gvsig.metadata.exceptions.MetadataException;
77
import org.gvsig.remoteclient.ogc.OGCClientOperation;
78
import org.gvsig.remoteclient.utils.BoundaryBox;
79
import org.gvsig.remoteclient.wfs.WFSClient;
80
import org.gvsig.remoteclient.wfs.WFSFeature;
81
import org.gvsig.remoteclient.wfs.WFSFeatureField;
82
import org.gvsig.remoteclient.wfs.WFSStatus;
83
import org.gvsig.remoteclient.wfs.exceptions.WFSException;
84
import org.gvsig.remoteclient.wfs.request.WFSGetFeatureRequestInformation;
85
import org.gvsig.remoteclient.wfs.request.WFSTransactionRequestInformation;
86
import org.gvsig.tools.ToolsLocator;
87
import org.gvsig.tools.dynobject.DynStruct;
88
import org.gvsig.xmlschema.lib.api.XMLSchemaLocator;
89
import org.gvsig.xmlschema.lib.api.XMLSchemaManager;
90
import org.gvsig.xmlschema.lib.api.som.IXSGeometryTypeDefinition;
91
import org.gvsig.xmlschema.lib.api.som.IXSTypeDefinition;
92
import org.slf4j.Logger;
93
import org.slf4j.LoggerFactory;
94

    
95
/**
96
 * @author <a href="mailto:jpiera@gvsig.org">Jorge Piera</a>
97
 */
98
public class WFSStoreProvider extends AbstractFeatureStoreProvider {
99
        private static final Logger logger = LoggerFactory
100
                        .getLogger(WFSStoreProvider.class);
101
        public static String NAME = "WFSStore";
102
        public static String DESCRIPTION = "WFS store to load WFS resources";
103

    
104
        private static final MetadataManager metadataManager = MetadataLocator
105
                        .getMetadataManager();
106
        private static final String METADATA_DEFINITION_NAME = "WFSStore";
107
        private static final String METADATA_DEFINITION_DESCRIPTION = "WFSStore metadata definition";
108

    
109
        // private IProjection projection;
110
        private long featureCount = -1;
111
        private boolean isKnownEnvelope = false;
112

    
113
        /**
114
         * If the user has selected the filter by area option
115
         */
116
        private boolean hasFilterByArea = false;
117

    
118
        /**
119
         * GML provider used by delegation to read the GML files
120
         */
121
        private GPEStoreProvider storeProviderDelegate = null;
122

    
123
        private static final DataManager dataManager = DALLocator.getDataManager();
124
        private static final XMLSchemaManager xmlSchemaManager = XMLSchemaLocator
125
                        .getXMLSchemaManager();
126

    
127
        boolean isFilterByAreaSupported = true;
128

    
129
        // WFS Parameters
130
        private WFSClient wfsClient;
131
        private WFSStatus wfsStatus;
132

    
133
        public WFSStoreProvider(DataStoreParameters params,
134
                        DataStoreProviderServices storeServices) throws InitializeException {
135
                super(
136
                                params,
137
                                storeServices,
138
                                ToolsLocator
139
                                                .getDynObjectManager()
140
                                                .createDynObject(
141
                                                                metadataManager
142
                                                                                .getDefinition(METADATA_DEFINITION_NAME)));
143
                initParams();
144
                try {
145
                        initFeatureType();
146
                } catch (WFSException e) {
147
                        throw new InitializeException(e);
148
                } catch (ReadException e) {
149
                        throw new InitializeException(e);
150
                }
151
        }
152

    
153
        private void initParams() throws InitializeException {
154
                try {
155
                        WFSOpenStoreParameters wfsParameters = getWFSParameters();
156
                        try {
157
                                if (wfsParameters.getVersion() == null) {
158
                                        wfsClient = new WFSClient(wfsParameters.getUrl(),
159
                                                        wfsParameters.getIgnoreCache());
160
                                        wfsParameters.setVersion(wfsClient.getVersion());
161
                                } else {
162
                                        wfsClient = new WFSClient(wfsParameters.getUrl(),
163
                                                        wfsParameters.getVersion(),
164
                                                        wfsParameters.getIgnoreCache());
165
                                }
166
                        } catch (IOException e) {
167
                                throw new InitializeException(e);
168
                        }
169
                        wfsStatus = new WFSStatus(wfsParameters.getFeatureType(),
170
                                        wfsParameters.getFeatureNamespace());
171
                        wfsStatus.setNamespacePrefix(wfsParameters.getFeaturePrefix());
172
                        wfsStatus.setFields(wfsParameters.getFields());
173

    
174
                        // Select the filter by area
175

    
176
                        Geometry filterByAreaGeometry = wfsParameters
177
                                        .getFilterByAreaGeometry();
178
                        Envelope filterByAreaEnvelope = wfsParameters
179
                                        .getFilterByAreaEnvelope();
180
                        if (filterByAreaGeometry != null) {
181
                                wfsStatus.setFilterByArea(filterByAreaGeometry,
182
                                                wfsParameters.getFilterByAreaAttribute(),
183
                                                wfsParameters.getFilterByAreaCrs().getFullCode(),
184
                                                wfsParameters.getFilterByAreaOperation());
185
                        } else if (filterByAreaEnvelope != null) {
186
                                wfsStatus.setFilterByArea(filterByAreaEnvelope,
187
                                                wfsParameters.getFilterByAreaAttribute(),
188
                                                wfsParameters.getFilterByAreaCrs().getFullCode(),
189
                                                wfsParameters.getFilterByAreaOperation());
190
                        }
191
                        this.hasFilterByArea = (wfsStatus.getFilterByArea() != null);
192

    
193
                        // Select the filter by attribute
194
                        wfsStatus.setFilterByAttribute(wfsParameters
195
                                        .getFilterEncodingByAttribute());
196

    
197
                        String _srs = wfsParameters.getCrs();
198
                        wfsStatus.setSrs(_srs);
199

    
200
                        wfsStatus.setTimeout(wfsParameters.getTimeOut());
201
                        wfsStatus.setMaxFeatures(wfsParameters.getMaxFeatures());
202
                        wfsStatus.setUserName(wfsParameters.getUser());
203
                        wfsStatus.setPassword(wfsParameters.getPassword());
204

    
205
                        // Setting the envelope for the layer
206
                        wfsClient.getCapabilities(wfsStatus, false, null);
207

    
208
                        Envelope envelope = calculateFullEnvelope();
209
                        if (envelope != null) {
210
                                this.setDynValue("Envelope", envelope);
211
                                isKnownEnvelope = true;
212
                        }
213
                } catch (WFSException e) {
214
                        throw new InitializeException("Impossible to retrieve the file", e);
215
                }
216
        }
217

    
218
        private WFSFeature getSelectedWFSFeature() throws ReadException,
219
                        WFSException {
220
                WFSOpenStoreParameters wfsParameters = getWFSParameters();
221

    
222
                return ((WFSServerExplorer) getExplorer()).getFeatureInfo(
223
                                wfsParameters.getFeatureNamespace(),
224
                                wfsParameters.getFeatureType());
225
        }
226

    
227
        private void initFeatureType() throws WFSException, ReadException {
228
                WFSFeature feature = getSelectedWFSFeature();
229

    
230
                if (feature == null) {
231
                        // TODO read from GML
232
                        throw new WFSException("It is not possible to parse the schema");
233
                }
234

    
235
                IProjection ipro = null;
236
                try {
237
                        ipro = CRSFactory.getCRS(wfsStatus.getSrs());
238
                        this.setDynValue("CRS", ipro);
239
                } catch (Exception ex) {
240
                        logger.info("Error: did not set CRS in store provider.", ex);
241
                }
242

    
243
                EditableFeatureType featureType = getStoreServices()
244
                                .createFeatureType();
245

    
246
                for (int i = 0; i < feature.getFieldSize(); i++) {
247
                        WFSFeatureField featureField = feature.getFieldAt(i);
248
                        int dataType = DataTypes.STRING;
249
                        String typeName = featureField.getType();
250
                        EditableFeatureAttributeDescriptor attributeDescriptor = null;
251

    
252
                        IXSTypeDefinition typeDefinition = null;
253

    
254
                        if (typeName != null) {
255
                                typeDefinition = xmlSchemaManager.getTypeDefinition(typeName);
256
                        }
257

    
258
                        if (typeDefinition != null) {
259
                                if (typeDefinition.getDataType() != null) {
260
                                        if (typeDefinition.getDataType().getType() == DataTypes.GEOMETRY) {
261
                                                dataType = typeDefinition.getDataType().getType();
262
                                        }
263
                                }
264
                                attributeDescriptor = featureType.add(featureField.getName(),
265
                                                dataType);
266
                                if (typeDefinition instanceof IXSGeometryTypeDefinition) {
267

    
268
                                        if (ipro != null) {
269
                                                attributeDescriptor.setSRS(ipro);
270
                                        } else {
271
                                                if (feature.getSrs().size() > 0) {
272
                                                        attributeDescriptor.setSRS(CRSFactory
273
                                                                        .getCRS((String) feature.getSrs().get(0)));
274
                                                } else {
275
                                                        logger.info("Unable to set CRS in feature type.");
276
                                                }
277
                                        }
278

    
279
                                        attributeDescriptor
280
                                                        .setGeometryType(((IXSGeometryTypeDefinition) typeDefinition)
281
                                                                        .getGeometryType());
282
                                        attributeDescriptor.setGeometrySubType(SUBTYPES.GEOM3D);
283
                                        featureType.setDefaultGeometryAttributeName(featureField
284
                                                        .getName());
285
                                }
286
                        } else {
287
                                attributeDescriptor = featureType.add(typeName, dataType);
288
                        }
289
                        // length, relevant for all (strings) except geometry
290
                        attributeDescriptor.setSize(128);
291
                }
292
                featureType.setHasOID(true);
293

    
294
                FeatureType defaultType = featureType.getNotEditableCopy();
295
                List types = new ArrayList(1);
296
                types.add(defaultType);
297
                this.getStoreServices().setFeatureTypes(types, defaultType);
298
        }
299

    
300
        private Envelope calculateFullEnvelope() {
301
                GeometryManager geometryManager = GeometryLocator.getGeometryManager();
302

    
303
                try {
304
                        WFSFeature feature = getSelectedWFSFeature();
305
                        if (feature != null) {
306
                                String _srs = wfsStatus.getSrs();
307
                                if (_srs != null) {
308

    
309
                                        BoundaryBox boundaryBox = feature.getBbox(_srs);
310
                                        // The projection is found
311
                                        if (boundaryBox != null) {
312
                                                return geometryManager.createEnvelope(
313
                                                                boundaryBox.getXmin(), boundaryBox.getYmin(),
314
                                                                boundaryBox.getXmax(), boundaryBox.getYmax(),
315
                                                                SUBTYPES.GEOM2D);
316
                                        }
317
                                        // Check if there is a latlon envelope
318
                                        boundaryBox = feature.getLatLonBbox();
319
                                        if (boundaryBox != null) {
320
                                                Envelope envelope = geometryManager.createEnvelope(
321
                                                                boundaryBox.getXmin(), boundaryBox.getYmin(),
322
                                                                boundaryBox.getXmax(), boundaryBox.getYmax(),
323
                                                                SUBTYPES.GEOM2D);
324
                                                if (!"EPSG:4326".equals(_srs)) {
325
                                                        IProjection sourceProjection = CRSFactory
326
                                                                        .getCRS("EPSG:4326");
327
                                                        IProjection destinationProjection = CRSFactory
328
                                                                        .getCRS(_srs);
329
                                                        if (destinationProjection != null) {
330
                                                                ICoordTrans coordTrans = sourceProjection
331
                                                                                .getCT(destinationProjection);
332
                                                                return envelope.convert(coordTrans);
333
                                                        }
334
                                                }
335
                                        }
336
                                } else {
337
                                        // If there is not a SRS is thrown a request for the first
338
                                        // 500 features
339
                                        int odlMaxFeatures = wfsStatus.getMaxFeatures();
340
                                        wfsStatus.setMaxFeatures(500);
341
                                        createSet(null, null);
342
                                        return storeProviderDelegate.getEnvelope();
343
                                }
344
                        }
345
                } catch (CreateEnvelopeException e) {
346
                        logger.error("Impossible to create an envelope", e);
347
                } catch (ReadException e) {
348
                        logger.error("Impossible to create an envelope", e);
349
                } catch (WFSException e) {
350
                        logger.error("Impossible to create an envelope", e);
351
                } catch (DataException e) {
352
                        logger.error("Impossible to create an envelope", e);
353
                }
354
                return null;
355
        }
356

    
357
        private WFSOpenStoreParameters getWFSParameters() {
358
                return (WFSOpenStoreParameters) getParameters();
359
        }
360

    
361
        /*
362
         * (non-Javadoc)
363
         *
364
         * @see org.gvsig.fmap.dal.store.gpe.GPEStoreProvider#open()
365
         */
366
        public void open() throws OpenException {
367
                try {
368
                        List featureTypes = this.getFeatureStore().getFeatureTypes();
369
                        for (int i = 0; i < featureTypes.size(); i++) {
370
                                FeatureType featureType = (FeatureType) featureTypes.get(i);
371
                        }
372
                } catch (DataException e) {
373
                        throw new OpenException("Reading the geometry type", e);
374
                }
375
        }
376

    
377
        protected static void registerMetadataDefinition() throws MetadataException {
378
                if (metadataManager.getDefinition(METADATA_DEFINITION_NAME) == null) {
379
                        DynStruct metadataDefinition = metadataManager.addDefinition(
380
                                        METADATA_DEFINITION_NAME, METADATA_DEFINITION_DESCRIPTION);
381

    
382
                        metadataDefinition.addDynFieldObject("Envelope")
383
                                        .setClassOfValue(Envelope.class).setMandatory(false);
384
                        metadataDefinition.addDynFieldObject("CRS")
385
                                        .setClassOfValue(IProjection.class).setMandatory(true);
386

    
387
                        metadataDefinition.extend(metadataManager
388
                                        .getDefinition(FeatureStore.METADATA_DEFINITION_NAME));
389
                }
390
        }
391

    
392
        /*
393
         * (non-Javadoc)
394
         *
395
         * @see
396
         * org.gvsig.fmap.dal.feature.spi.AbstractFeatureStoreProvider#getExplorer()
397
         */
398
        public DataServerExplorer getExplorer() throws ReadException {
399
                DataManager manager = DALLocator.getDataManager();
400
                WFSServerExplorerParameters params;
401
                try {
402
                        params = (WFSServerExplorerParameters) manager
403
                                        .createServerExplorerParameters(WFSServerExplorer.NAME);
404
                        params.setUrl(wfsClient.getHost());
405
                        return manager.openServerExplorer(WFSServerExplorer.NAME, params);
406
                } catch (Exception e) {
407
                        throw new ReadException(this.getName(), e);
408
                }
409
        }
410

    
411
        public String getProviderName() {
412
                return NAME;
413
        }
414

    
415
        public FeatureSetProvider createSet(FeatureQuery query)
416
                        throws DataException {
417
                return createSet(query, null);
418
        }
419

    
420
        public FeatureSetProvider createSet(FeatureQuery query,
421
                        FeatureType featureType) throws DataException {
422
                if ((featureCount == -1) || (storeProviderDelegate == null)
423
                                || (featureCount >= wfsStatus.getMaxFeatures())) {
424

    
425
                        File file = executeSpatialQuery();
426

    
427
                        storeProviderDelegate = createProvider(file);
428
                }
429

    
430
                return storeProviderDelegate.createSet(query, featureType);
431
        }
432

    
433
        /**
434
         * It creates the provider that is used to retrieve features from a file.
435
         *
436
         * @param file
437
         *            the file that contains the downloaded file
438
         * @return
439
         * @throws InitializeException
440
         * @throws ProviderNotRegisteredException
441
         */
442
        private GPEStoreProvider createProvider(File file)
443
                        throws InitializeException, ProviderNotRegisteredException {
444
                return new GPEStoreProvider(createStoreParameters(file),
445
                                getStoreServices());
446
        }
447

    
448
        private DataStoreParameters createStoreParameters(File file)
449
                        throws InitializeException, ProviderNotRegisteredException {
450
                DataStoreParameters parameters = dataManager
451
                                .createStoreParameters(GPEStoreProvider.NAME);
452

    
453
                parameters.setDynValue("File", file.getAbsolutePath());
454
                parameters.setDynValue("Envelope", this.getDynValue("Envelope"));
455
                parameters.setDynValue("useAxisOrderYX", this.getWFSParameters()
456
                                .getUseAxisOrderYX());
457
                parameters.setDynValue("Crs", this.getWFSParameters().getCrs());
458
                return parameters;
459
        }
460

    
461
        private File executeSpatialQuery() throws DataException {
462
                try {
463
                        Envelope filterByAreaEnvelope = getWFSParameters()
464
                                        .getFilterByAreaEnvelope();
465
                        Geometry filterByAreaGeometry = getWFSParameters()
466
                                        .getFilterByAreaGeometry();
467
                        if (filterByAreaEnvelope != null) {
468
                                String crs = getWFSParameters().getCrs();
469
                                String the_geom = getWFSParameters().getFilterByAreaAttribute();
470
                                int operator = getWFSParameters().getFilterByAreaOperation();
471

    
472
                                IProjection envelopeCrs = this.getWFSParameters().getFilterByAreaCrs();
473

    
474
                                if (!crs.equalsIgnoreCase(envelopeCrs.getFullCode())) {
475
                                        Envelope envelope = null;
476
                                        try {
477
                                                envelope = (Envelope) filterByAreaEnvelope.clone();
478
                                        } catch (CloneNotSupportedException e) {
479
                                                // Do nothing
480
                                        }
481
                                        ICoordTrans ct = envelopeCrs.getCT(CRSFactory.getCRS(crs));
482
                                        filterByAreaEnvelope = envelope.convert(ct);
483
                                }
484

    
485
                                if (this.getWFSParameters().getUseAxisOrderYX()) {
486
                                        Envelope envelope = null;
487
                                        try {
488
                                                envelope = (Envelope) filterByAreaEnvelope.clone();
489
                                        } catch (CloneNotSupportedException e) {
490
                                                // Do nothing
491
                                        }
492
                                        double x = envelope.getLowerCorner().getX();
493
                                        envelope.getLowerCorner().setX(
494
                                                        envelope.getLowerCorner().getY());
495
                                        envelope.getLowerCorner().setY(x);
496

    
497
                                        x = envelope.getUpperCorner().getX();
498
                                        envelope.getUpperCorner().setX(
499
                                                        envelope.getUpperCorner().getY());
500
                                        envelope.getUpperCorner().setY(x);
501
                                        filterByAreaEnvelope = envelope;
502
                                }
503
                                wfsStatus.setFilterByArea(filterByAreaEnvelope, the_geom, crs,
504
                                                operator);
505
                        } else if (filterByAreaGeometry != null) {
506
                                String crs = getWFSParameters().getCrs();
507
                                String the_geom = getWFSParameters().getFilterByAreaAttribute();
508
                                int operator = getWFSParameters().getFilterByAreaOperation();
509

    
510
                                IProjection geometryCrs = this.getWFSParameters().getFilterByAreaCrs();
511

    
512
                                if (!crs.equalsIgnoreCase(geometryCrs.getFullCode())) {
513
                                        Geometry geom = null;
514
                                        geom = (Geometry) filterByAreaGeometry.cloneGeometry();
515
                                        ICoordTrans ct = geometryCrs.getCT(CRSFactory.getCRS(crs));
516
                                        geom.reProject(ct);
517
                                        filterByAreaGeometry = geom;
518
                                }
519

    
520
                                if (this.getWFSParameters().getUseAxisOrderYX()) {
521
                                        Geometry geom = filterByAreaGeometry.cloneGeometry();
522
                                        AffineTransform at = new AffineTransform(0, 1, 1, 0, 0, 1);
523
                                        geom.transform(at);
524
                                        filterByAreaGeometry = geom;
525
                                }
526
                                wfsStatus.setFilterByArea(filterByAreaGeometry, the_geom, crs,
527
                                                operator);
528

    
529
                        }
530
                        wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_POST);
531
                        // If it is not possible to calculate the
532
                        wfsStatus.setResultType(WFSStatus.RESULTYPE_RESULTS);
533
                        return wfsClient.getFeature(wfsStatus, getWFSParameters()
534
                                        .getIgnoreCache(), null);
535
                } catch (WFSException e) {
536
                        throw new InitializeException("Impossible to retrieve the file", e);
537
                }
538
        }
539

    
540
        public Object getSourceId() {
541
                StringBuffer sourceID = new StringBuffer(getWFSParameters().getUrl());
542
                sourceID.append("_" + getWFSParameters().getFeatureType());
543
                int hash = sourceID.hashCode();
544
                if (sourceID.length() > 60) {
545
                        return sourceID.substring(0, 60) + "_" + hash;
546
                } else {
547
                        return sourceID.toString() + "_" + hash;
548
                }
549
        }
550

    
551
        public Object createNewOID() {
552
                try {
553
                        return String.valueOf(getFeatureCount() + 1);
554
                } catch (DataException e) {
555
                        return String.valueOf(Math.random());
556
                }
557
        }
558

    
559
        public long getFeatureCount() throws DataException {
560
                if (featureCount == -1) {
561
                        wfsStatus.setResultType(WFSStatus.RESULTYPE_HITS);
562
                                // The filter encoding is better supported using POST
563
                                if (hasFilterByArea) {
564
                                        wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_POST);
565
                                } else {
566
                                        wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_GET);
567
                                }
568
                                File file = executeSpatialQuery();
569
                                featureCount = ((WFSGetFeatureRequestInformation) wfsClient
570
                                                .getLastWfsRequestInformation()).getNumberOfFeatures();
571
                                // If the service doesn't support RESULTTYPE_HITS, parse the
572
                                // file and get the FeatureCount
573
                                if (featureCount == -1) {
574
                                        storeProviderDelegate = createProvider(file);
575
                                        featureCount = storeProviderDelegate.getFeatureCount();
576
                                }
577
                }
578
                return featureCount;
579
        }
580

    
581
        public int getOIDType() {
582
                return DataTypes.STRING;
583
        }
584

    
585
        public ResourceProvider getResource() {
586
                return storeProviderDelegate.getResource();
587
        }
588

    
589
        protected FeatureProvider internalGetFeatureProviderByReference(
590
                        FeatureReferenceProviderServices reference, FeatureType featureType)
591
                        throws DataException {
592
                return storeProviderDelegate.internalGetFeatureProviderByReference(
593
                                reference, featureType);
594
        }
595

    
596
        public String getFullName() {
597
                return getWFSParameters().getUrl() + "_"
598
                                + getWFSParameters().getFeatureType();
599
        }
600

    
601
        public String getName() {
602
                return getWFSParameters().getFeatureType();
603
        }
604

    
605
        public boolean isKnownEnvelope() {
606
                return isKnownEnvelope;
607
        }
608

    
609
        public boolean hasRetrievedFeaturesLimit() {
610
                return true;
611
        }
612

    
613
        public int getRetrievedFeaturesLimit() {
614
                // WFS 1.0.0 can not know where is the limit
615
                if (getWFSParameters().getVersion().equals("1.0.0")) {
616
                        return 0;
617
                } else {
618
                        return wfsClient.getServiceInformation().getMaxFeatures();
619
                }
620
        }
621

    
622
        public void performChanges(Iterator deleteds, Iterator inserteds,
623
                        Iterator updateds, Iterator featureTypesChanged)
624
                        throws DataException {
625
                wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_POST);
626
                WFSTTransactionBuilder transactionBuilder = new WFSTTransactionBuilder(
627
                                wfsStatus, wfsClient);
628

    
629
                // Create the Query
630
                try {
631
                        // Add new features
632
                        while (inserteds.hasNext()) {
633
                                transactionBuilder.addInsertFeature((FeatureProvider) inserteds
634
                                                .next());
635
                        }
636
                        // Add deleted features
637
                        while (deleteds.hasNext()) {
638
                                transactionBuilder
639
                                                .addDeleteFeature(internalGetFeatureProviderByReference(
640
                                                                (FeatureReferenceProviderServices) deleteds
641
                                                                                .next(), null).getOID().toString());
642
                                ;
643
                        }
644
                        // Add updated features
645
                        while (updateds.hasNext()) {
646
                                transactionBuilder.addUpdateFeature((FeatureProvider) updateds
647
                                                .next());
648
                        }
649
                } catch (WriterHandlerCreationException e) {
650
                        throw new WFSTTRansactionException(e);
651
                } catch (GeometryOperationNotSupportedException e) {
652
                        throw new WFSTTRansactionException(e);
653
                } catch (GeometryOperationException e) {
654
                        throw new WFSTTRansactionException(e);
655
                }
656

    
657
                // Send the query to the server
658
                try {
659
                        wfsClient.transaction(wfsStatus, true, null);
660
                        WFSTransactionRequestInformation transactionRequestInformation = (WFSTransactionRequestInformation) wfsClient
661
                                        .getLastWfsRequestInformation();
662
                        if (transactionRequestInformation.getStatus() == WFSTransactionRequestInformation.STATUS_FAILED) {
663
                                throw new WFSTTRansactionException(
664
                                                transactionRequestInformation.getMessage());
665
                        }
666
                } catch (WFSException e) {
667
                        throw new WFSTTRansactionException(e);
668
                }
669
        }
670

    
671
        public boolean allowWrite() {
672
                return wfsClient.getServiceInformation().isOperationSupported(
673
                                "Transaction");
674
        }
675

    
676
        public Envelope getEnvelope() throws DataException {
677
                return (Envelope) this.getDynValue("Envelope");
678
        }
679

    
680
        public FeatureProvider createFeatureProvider(FeatureType type)
681
                        throws DataException {
682
                return super.createFeatureProvider(type);
683
        }
684

    
685
}