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 @ 10

History | View | Annotate | Download (25.2 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.io.File;
31
import java.io.IOException;
32
import java.util.ArrayList;
33
import java.util.Iterator;
34
import java.util.List;
35

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

    
98

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

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

    
111
    // private IProjection projection;        
112
    private long featureCount = -1;
113
    private boolean isKnownEnvelope = false;
114

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

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

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

    
128
    boolean isFilterByAreaSupported = true;
129

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

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

    
149
    private void initParams() throws InitializeException{
150
        try {
151
            WFSStoreParameters wfsParameters = getWFSParameters();
152
            try {
153
                if (wfsParameters.getVersion() == null){
154
                    wfsClient = new WFSClient(wfsParameters.getUrl());
155
                    wfsParameters.setVersion(wfsClient.getVersion());
156
                }else{
157
                    wfsClient = new WFSClient(wfsParameters.getUrl(), wfsParameters.getVersion());
158
                }
159
            } catch (IOException e) {
160
                throw new InitializeException(e);
161
            }
162
            wfsStatus = new WFSStatus( wfsParameters.getFeatureType(),
163
                wfsParameters.getFeatureNamespace());
164
            wfsStatus.setNamespacePrefix(wfsParameters.getFeaturePrefix());
165
            wfsStatus.setFields(wfsParameters.getFields());
166

    
167
            //Select the filter by area
168
            wfsStatus.setFilterByArea(wfsParameters.getFilterByAreaGeometry(), wfsParameters.getFilterByAreaAttribute(), 
169
                wfsParameters.getFilterByAreaCrs(), wfsParameters.getFilterByAreaOperation());
170
            this.hasFilterByArea = (wfsStatus.getFilterByArea() != null);
171

    
172
            //Select the filter by attribute
173
            wfsStatus.setFilterByAttribute(wfsParameters.getFilterEncodingByAttribute());
174
            
175
            String _srs = wfsParameters.getFilterByAreaCrs();
176
            wfsStatus.setSrs(_srs);
177

    
178
            wfsStatus.setTimeout(wfsParameters.getTimeOut());
179
            wfsStatus.setMaxFeatures(wfsParameters.getMaxFeatures());
180
            wfsStatus.setUserName(wfsParameters.getUser());
181
            wfsStatus.setPassword(wfsParameters.getPassword());
182

    
183
            //Setting the envelope for the layer
184
            wfsClient.getCapabilities(wfsStatus, false, null);
185

    
186
            Envelope envelope = calculateFullEnvelope();
187
            if (envelope != null){
188
                this.setDynValue("Envelope", envelope);
189
                isKnownEnvelope = true;
190
            }                        
191
        } catch (WFSException e) {
192
            throw new InitializeException("Impossible to retrieve the file", e);
193
        }
194
    }
195

    
196
    private WFSFeature getSelectedWFSFeature() throws ReadException, WFSException{
197
        WFSStoreParameters wfsParameters = getWFSParameters();
198

    
199
        return  ((WFSServerExplorer)getExplorer()).getFeatureInfo(wfsParameters.getFeatureNamespace(),
200
            wfsParameters.getFeatureType());
201
    }
202

    
203
    private void initFeatureType() throws WFSException, ReadException{           
204
        WFSFeature feature  = getSelectedWFSFeature();
205

    
206
        if (feature == null){
207
            //TODO read from GML
208
            throw new WFSException("It is not possible to parse the schema");
209
        }
210

    
211
        IProjection ipro = null;
212
        try {
213
            ipro = CRSFactory.getCRS(wfsStatus.getSrs());
214
            this.setDynValue("CRS", ipro);
215
        } catch (Exception ex) {
216
            logger.info("Error: did not set CRS in store provider.", ex);
217
        }
218

    
219
        EditableFeatureType featureType = getStoreServices().createFeatureType();
220

    
221
        for (int i=0 ; i<feature.getFieldSize() ; i++){       
222
            WFSFeatureField featureField = feature.getFieldAt(i);           
223
            int dataType = DataTypes.STRING;               
224
            String typeName = featureField.getType();
225
            EditableFeatureAttributeDescriptor attributeDescriptor = null;
226

    
227
            IXSTypeDefinition typeDefinition = null;
228
            
229
            if (typeName != null){
230
                typeDefinition = xmlSchemaManager.getTypeDefinition(typeName);
231
            }
232
            
233
            if (typeDefinition != null){             
234
                if (typeDefinition.getDataType() != null){
235
                    if (typeDefinition.getDataType().getType() == DataTypes.GEOMETRY){
236
                        dataType = typeDefinition.getDataType().getType();
237
                    }
238
                }
239
                attributeDescriptor = featureType.add(featureField.getName(), dataType);   
240
                if (typeDefinition instanceof IXSGeometryTypeDefinition){
241
                    if (feature.getSrs().size() > 0){
242
                        attributeDescriptor.setSRS(CRSFactory.getCRS((String)feature.getSrs().get(0)));
243
                    }                    
244
                    attributeDescriptor.setGeometryType(((IXSGeometryTypeDefinition)typeDefinition).getGeometryType());
245
                    attributeDescriptor.setGeometrySubType(SUBTYPES.GEOM3D);
246
                    featureType.setDefaultGeometryAttributeName(featureField.getName());
247
                }                               
248
            }else{
249
                attributeDescriptor = featureType.add(typeName, dataType);    
250
            }                 
251
        }       
252
        featureType.setHasOID(true);
253

    
254
        FeatureType defaultType = featureType.getNotEditableCopy();
255
        List types = new ArrayList(1);
256
        types.add(defaultType);
257
        this.getStoreServices().setFeatureTypes(types, defaultType);
258
    }
259

    
260
    private Envelope calculateFullEnvelope() {
261
        GeometryManager geometryManager = GeometryLocator.getGeometryManager();
262

    
263
        try{
264
            WFSFeature feature  = getSelectedWFSFeature();
265
            if (feature != null){ 
266
                String _srs = wfsStatus.getSrs();
267
                if (_srs != null) {
268

    
269
                    BoundaryBox boundaryBox = feature.getBbox(_srs);
270
                    //The projection is found
271
                    if (boundaryBox != null){
272
                        return geometryManager.createEnvelope(boundaryBox.getXmin(),
273
                            boundaryBox.getYmin(), boundaryBox.getXmax(), boundaryBox.getYmax(), SUBTYPES.GEOM2D);
274
                    }
275
                    //Check if there is a latlon envelope
276
                    boundaryBox = feature.getLatLonBbox();
277
                    if (boundaryBox != null){
278
                        Envelope envelope = geometryManager.createEnvelope(boundaryBox.getXmin(),
279
                            boundaryBox.getYmin(), boundaryBox.getXmax(), boundaryBox.getYmax(), SUBTYPES.GEOM2D);
280
                        if (!"EPSG:4326".equals(_srs)){
281
                            IProjection sourceProjection = CRSFactory.getCRS("EPSG:4326");
282
                            IProjection destinationProjection = CRSFactory.getCRS(_srs);
283
                            if (destinationProjection != null){
284
                                ICoordTrans coordTrans = sourceProjection.getCT(destinationProjection);
285
                                return envelope.convert(coordTrans);
286
                            }        
287
                        }
288
                    }
289
                }else{
290
                    //If there is not a SRS is thrown a request for the first 500 features
291
                    int odlMaxFeatures = wfsStatus.getMaxFeatures();
292
                    wfsStatus.setMaxFeatures(500);
293
                    createSet(null, null);
294
                    return storeProviderDelegate.getEnvelope();
295
                }
296
            }
297
        }catch(CreateEnvelopeException e){
298
            logger.error("Impossible to create an envelope", e);
299
        } catch (ReadException e) {
300
            logger.error("Impossible to create an envelope", e);
301
        } catch (WFSException e) {
302
            logger.error("Impossible to create an envelope", e);
303
        } catch (DataException e) {
304
            logger.error("Impossible to create an envelope", e);
305
        }
306
        return null;
307
    }
308

    
309
    private WFSStoreParameters getWFSParameters() {
310
        return (WFSStoreParameters) getParameters();
311
    }
312

    
313
    /* (non-Javadoc)
314
     * @see org.gvsig.fmap.dal.store.gpe.GPEStoreProvider#open()
315
     */
316
    public void open() throws OpenException {
317
        try {
318
            List featureTypes = this.getFeatureStore().getFeatureTypes();
319
            for (int i=0 ; i<featureTypes.size() ; i++){
320
                FeatureType featureType = (FeatureType)featureTypes.get(i);
321
            }
322
        } catch (DataException e) {
323
            throw new OpenException("Reading the geometry type", e);
324
        }
325
    }
326

    
327
    protected static void registerMetadataDefinition() throws MetadataException {       
328
        if (metadataManager.getDefinition(METADATA_DEFINITION_NAME) == null) {
329
            DynStruct metadataDefinition = metadataManager.addDefinition(
330
                METADATA_DEFINITION_NAME, METADATA_DEFINITION_DESCRIPTION);
331

    
332
            metadataDefinition.addDynFieldObject("Envelope").setClassOfValue(Envelope.class).setMandatory(false);
333
            metadataDefinition.addDynFieldObject("CRS").setClassOfValue(IProjection.class).setMandatory(true);
334

    
335
            metadataDefinition.extend(metadataManager
336
                .getDefinition(FeatureStore.METADATA_DEFINITION_NAME));
337
        }
338
    }
339

    
340
    /* (non-Javadoc)
341
     * @see org.gvsig.fmap.dal.feature.spi.AbstractFeatureStoreProvider#getExplorer()
342
     */
343
    public DataServerExplorer getExplorer() throws ReadException {
344
        DataManager manager = DALLocator.getDataManager();
345
        WFSServerExplorerParameters params;
346
        try {
347
            params = (WFSServerExplorerParameters) manager
348
            .createServerExplorerParameters(WFSServerExplorer.NAME);
349
            params.setUrl(wfsClient.getHost());
350
            return manager.openServerExplorer(WFSServerExplorer.NAME,params);
351
        } catch (Exception e) {
352
            throw new ReadException(this.getName(), e);
353
        }
354
    }
355

    
356
    public String getProviderName() {
357
        return NAME;
358
    }
359

    
360
    public FeatureSetProvider createSet(FeatureQuery query)
361
    throws DataException {
362
        return createSet(query, null);
363
    }
364

    
365
    public FeatureSetProvider createSet(FeatureQuery query,
366
        FeatureType featureType) throws DataException {
367
        if ((featureCount == -1) ||
368
            (storeProviderDelegate == null) ||
369
            (featureCount >= wfsStatus.getMaxFeatures())){ 
370

    
371
            File file = null;
372

    
373
            if (query == null){
374
                file = executeQuery();   
375
            }else{
376
                //If it is possible to execute a spatial query...
377
                if ((query.getFilter() != null) && (!hasFilterByArea)){
378
                    file = executeSpatialQuery(query);
379
                }else{
380
                    file = executeQuery();   
381
                }        
382

    
383
            }
384
            storeProviderDelegate = createProvider(file);
385
        }
386
        
387
        return storeProviderDelegate.createSet(query, featureType);
388
    }
389

    
390
    /**
391
     * It creates the provider that is used to retrieve features from a file.
392
     * @param file
393
     * the file that contains the downloaded file
394
     * @return
395
     * @throws InitializeException
396
     * @throws ProviderNotRegisteredException
397
     */
398
    private GPEStoreProvider createProvider(File file) throws InitializeException, ProviderNotRegisteredException{
399
        return new GPEStoreProvider(createStoreParameters(file), getStoreServices());
400
    }        
401

    
402
    private DataStoreParameters createStoreParameters(File file) throws InitializeException, ProviderNotRegisteredException{
403
        DataStoreParameters parameters = dataManager.createStoreParameters(GPEStoreProvider.NAME);
404

    
405
        parameters.setDynValue("File", file.getAbsolutePath());
406
        parameters.setDynValue("Envelope", this.getDynValue("Envelope"));
407
        return parameters;
408
    }
409

    
410
    /**
411
     * It executes a wfs Query without spatial filter
412
     * @throws DataException
413
     */
414
    private File executeQuery() throws DataException{
415
        try{
416
            wfsStatus.setResultType(WFSStatus.RESULTYPE_RESULTS);
417
            if (!hasFilterByArea){
418
                wfsStatus.removeFilterByArea();
419
            }
420
            return wfsClient.getFeature(wfsStatus, true, null);
421
        } catch (WFSException e) {
422
            throw new InitializeException("Impossible to retrieve the file", e);
423
        }
424
    }
425

    
426
    /**
427
     * Executes a new query sending the FilterEncoding request to the server
428
     * @param query
429
     * The Query to send
430
     * @throws InitializeException
431
     * If there is a problem with the request or the parsing process
432
     */
433
    private File executeSpatialQuery(FeatureQuery query) throws DataException{
434
        EvaluatorFieldsInfo fieldsInfo = query.getFilter().getFieldsInfo();
435
        String[] fields = fieldsInfo.getFieldNames();
436
        for (int i=0 ; i<fields.length ; i++){
437
            EvaluatorFieldValue[] evaluatorFieldValues = fieldsInfo.getFieldValues(fields[i]);
438
            for (int j=0 ; j<evaluatorFieldValues.length ; j++){                                
439
                if (EvaluatorFieldValue.MATCH == evaluatorFieldValues[j].getType()){
440
                    EvaluatorFieldValueMatch evaluatorFieldValueMatch = (EvaluatorFieldValueMatch)evaluatorFieldValues[j];
441
                    Object area = evaluatorFieldValueMatch.getValue();
442
                    if (area instanceof Envelope){
443
                        return executeSpatialQueryFromEnvelope(evaluatorFieldValueMatch.getFieldName(),
444
                            (Envelope)area);                                        
445
                    }else if (area instanceof Geometry){
446
                        return executeSpatialQueryFromGeometry(evaluatorFieldValueMatch.getFieldName(),
447
                            (Geometry)area);                                                
448
                    }
449
                }
450
            }                        
451
        }
452
        return null;
453
    }
454

    
455
    private File executeSpatialQueryFromGeometry(String the_geom, Geometry geometry) throws DataException{
456
        wfsStatus.setFilterByArea(geometry, the_geom, wfsStatus.getSrs(), 
457
            FilterEncoding.GEOMETRIC_OPERATOR_CONTAINS);
458
        return executeSpatialQuery();
459
    }
460

    
461
    private File executeSpatialQueryFromEnvelope(String the_geom, Envelope envelope) throws DataException{
462
        wfsStatus.setFilterByArea(envelope, the_geom, wfsStatus.getSrs(), 
463
            FilterEncoding.GEOMETRIC_OPERATOR_CONTAINS);                
464
        return executeSpatialQuery();
465
    }
466

    
467
    private File executeSpatialQuery() throws DataException{
468
        try {
469
            wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_POST);
470
            //If it is not possible to calculate the 
471
            wfsStatus.setResultType(WFSStatus.RESULTYPE_RESULTS);
472
            return wfsClient.getFeature(wfsStatus, true, null);
473
        } catch (WFSException e) {
474
            throw new InitializeException("Impossible to retrieve the file", e);
475
        }
476
    }                
477

    
478
    public Object getSourceId() {
479
        StringBuffer sourceID = new StringBuffer(getWFSParameters().getUrl());
480
        sourceID.append("_" + getWFSParameters().getFeatureType());
481
        int hash = sourceID.hashCode();
482
        if (sourceID.length() > 60){
483
            return sourceID.substring(0, 60) + "_" + hash;
484
        }else{
485
            return sourceID.toString() + "_" + hash;
486
        }
487
    }
488
   
489
    public Object createNewOID() {        
490
        try {
491
            return String.valueOf(getFeatureCount()+1);
492
        } catch (DataException e) {
493
            return String.valueOf(Math.random());
494
        }
495
    }
496

    
497
    public long getFeatureCount() throws DataException {
498
        if (featureCount == -1){
499
            wfsStatus.setResultType(WFSStatus.RESULTYPE_HITS);
500
            try {
501
                //The filter encoding is better supported using POST
502
                if (hasFilterByArea){
503
                    wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_POST);
504
                }else{
505
                    wfsStatus.setProtocol(OGCClientOperation.PROTOCOL_GET);
506
                }
507
                File file = wfsClient.getFeature(wfsStatus, true, null);
508
                featureCount = ((WFSGetFeatureRequestInformation)wfsClient.getLastWfsRequestInformation()).getNumberOfFeatures();
509
                //If the service doesn't support RESULTTYPE_HITS, parse the file and get the FeatureCount
510
                if (featureCount == -1){
511
                    storeProviderDelegate = createProvider(file);
512
                    featureCount = storeProviderDelegate.getFeatureCount();
513
                }
514
            } catch (WFSException e) {
515
                throw new ConnectionServerException("Error calculating the feature count", e);
516
            }
517
        }
518
        return featureCount;
519
    }
520

    
521
    public int getOIDType() {
522
        return DataTypes.STRING;
523
    }
524

    
525
    public ResourceProvider getResource() {
526
        return storeProviderDelegate.getResource();
527
    }
528

    
529
    protected FeatureProvider internalGetFeatureProviderByReference(
530
        FeatureReferenceProviderServices reference, FeatureType featureType)
531
    throws DataException {
532
        return storeProviderDelegate.internalGetFeatureProviderByReference(reference, featureType);
533
    }
534

    
535
    public String getFullName() {       
536
        return getWFSParameters().getUrl() + "_" + getWFSParameters().getFeatureType();
537
    }
538

    
539
    public String getName() {        
540
        return getFullName();
541
    }
542

    
543
    public boolean isKnownEnvelope(){  
544
        return isKnownEnvelope;
545
    }
546

    
547
    public boolean hasRetrievedFeaturesLimit(){
548
        return true;
549
    }
550

    
551
    public int getRetrievedFeaturesLimit(){
552
        //WFS 1.0.0 can not know where is the limit
553
        if (getWFSParameters().getVersion().equals("1.0.0")){
554
            return 0;
555
        }else{
556
            return wfsClient.getServiceInformation().getMaxFeatures();
557
        }
558
    }
559

    
560
    public void performChanges(Iterator deleteds, Iterator inserteds,
561
        Iterator updateds, Iterator featureTypesChanged)
562
    throws DataException {
563
        WFSTTransactionBuilder transactionBuilder = new WFSTTransactionBuilder(wfsStatus, wfsClient);
564

    
565
        //Create the Query
566
        try {
567
            //Add new features
568
            while (inserteds.hasNext()){
569
                transactionBuilder.addInsertFeature((FeatureProvider)inserteds.next());
570
            }
571
            //Add deleted features
572
            while (deleteds.hasNext()){
573
                transactionBuilder.addDeleteFeature(
574
                    internalGetFeatureProviderByReference((FeatureReferenceProviderServices)deleteds.next(), null).getOID().toString());;
575
            }
576
            //Add updated features
577
            while (updateds.hasNext()){
578
                transactionBuilder.addUpdateFeature((FeatureProvider)updateds.next());
579
            }
580
        } catch (WriterHandlerCreationException e) {
581
            throw new WFSTTRansactionException(e);
582
        } catch (GeometryOperationNotSupportedException e) {
583
            throw new WFSTTRansactionException(e);
584
        } catch (GeometryOperationException e) {
585
            throw new WFSTTRansactionException(e);
586
        }
587
        
588
        //Send the query to the server
589
        try {
590
            wfsClient.transaction(wfsStatus, true, null);
591
            WFSTransactionRequestInformation transactionRequestInformation =  (WFSTransactionRequestInformation)wfsClient.getLastWfsRequestInformation();
592
            if (transactionRequestInformation.getStatus() == WFSTransactionRequestInformation.STATUS_FAILED){
593
                throw new WFSTTRansactionException(transactionRequestInformation.getMessage());
594
            }
595
        } catch (WFSException e) {
596
            throw new WFSTTRansactionException(e);
597
        }
598
    }
599

    
600
    public boolean allowWrite() {
601
        return wfsClient.getServiceInformation().isOperationSupported("Transaction");
602
    }
603

    
604
    public Envelope getEnvelope() throws DataException {        
605
        return (Envelope) this.getDynValue("Envelope");
606
    }
607

    
608
    public FeatureProvider createFeatureProvider(FeatureType type)
609
    throws DataException {       
610
        return super.createFeatureProvider(type);
611
    }
612

    
613

    
614
}
615