1 /****************************************************************************** 2 * $Id: ogr_wfs.h 29273 2015-06-02 08:08:38Z rouault $ 3 * 4 * Project: WFS Translator 5 * Purpose: Definition of classes for OGR WFS driver. 6 * Author: Even Rouault, even dot rouault at mines dash paris dot org 7 * 8 ****************************************************************************** 9 * Copyright (c) 2010-2013, Even Rouault <even dot rouault at mines-paris dot org> 10 * 11 * Permission is hereby granted, free of charge, to any person obtaining a 12 * copy of this software and associated documentation files (the "Software"), 13 * to deal in the Software without restriction, including without limitation 14 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 15 * and/or sell copies of the Software, and to permit persons to whom the 16 * Software is furnished to do so, subject to the following conditions: 17 * 18 * The above copyright notice and this permission notice shall be included 19 * in all copies or substantial portions of the Software. 20 * 21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 22 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 23 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 24 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 25 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 26 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 27 * DEALINGS IN THE SOFTWARE. 28 ****************************************************************************/ 29 30 #ifndef _OGR_WFS_H_INCLUDED 31 #define _OGR_WFS_H_INCLUDED 32 33 #include <vector> 34 #include <set> 35 #include <map> 36 37 #include "cpl_minixml.h" 38 #include "ogrsf_frmts.h" 39 #include "gmlreader.h" 40 #include "cpl_http.h" 41 #include "swq.h" 42 43 CPLXMLNode* WFSFindNode(CPLXMLNode* psXML, const char* pszRootName); 44 void OGRWFSRecursiveUnlink( const char *pszName ); 45 CPLString WFS_TurnSQLFilterToOGCFilter( const swq_expr_node* poExpr, 46 OGRDataSource* poDS, 47 OGRFeatureDefn* poFDefn, 48 int nVersion, 49 int bPropertyIsNotEqualToSupported, 50 int bUseFeatureId, 51 int bGmlObjectIdNeedsGMLPrefix, 52 const char* pszNSPrefix, 53 int* pbOutNeedsNullCheck); 54 swq_custom_func_registrar* WFSGetCustomFuncRegistrar(); 55 56 const char* FindSubStringInsensitive(const char* pszStr, 57 const char* pszSubStr); 58 59 CPLString WFS_EscapeURL(const char* pszURL); 60 CPLString WFS_DecodeURL(const CPLString &osSrc); 61 62 class OGRWFSSortDesc 63 { 64 public: 65 CPLString osColumn; 66 int bAsc; 67 OGRWFSSortDesc(const CPLString & osColumn,int bAsc)68 OGRWFSSortDesc(const CPLString& osColumn, int bAsc) : osColumn(osColumn), bAsc(bAsc) {} OGRWFSSortDesc(const OGRWFSSortDesc & other)69 OGRWFSSortDesc(const OGRWFSSortDesc& other) : osColumn(other.osColumn), bAsc(other.bAsc) {} 70 }; 71 72 /************************************************************************/ 73 /* OGRWFSLayer */ 74 /************************************************************************/ 75 76 class OGRWFSDataSource; 77 78 class OGRWFSLayer : public OGRLayer 79 { 80 OGRWFSDataSource* poDS; 81 82 OGRFeatureDefn* poFeatureDefn; 83 int bGotApproximateLayerDefn; 84 GMLFeatureClass* poGMLFeatureClass; 85 86 int bAxisOrderAlreadyInverted; 87 OGRSpatialReference *poSRS; 88 89 char* pszBaseURL; 90 char* pszName; 91 char* pszNS; 92 char* pszNSVal; 93 94 int bStreamingDS; 95 GDALDataset *poBaseDS; 96 OGRLayer *poBaseLayer; 97 int bHasFetched; 98 int bReloadNeeded; 99 100 CPLString osGeometryColumnName; 101 OGRwkbGeometryType eGeomType; 102 GIntBig nFeatures; 103 int bCountFeaturesInGetNextFeature; 104 105 int CanRunGetFeatureCountAndGetExtentTogether(); 106 107 CPLString MakeGetFeatureURL(int nMaxFeatures, int bRequestHits); 108 int MustRetryIfNonCompliantServer(const char* pszServerAnswer); 109 GDALDataset* FetchGetFeature(int nMaxFeatures); 110 OGRFeatureDefn* DescribeFeatureType(); 111 GIntBig ExecuteGetFeatureResultTypeHits(); 112 113 double dfMinX, dfMinY, dfMaxX, dfMaxY; 114 int bHasExtents; 115 116 OGRGeometry *poFetchedFilterGeom; 117 118 CPLString osSQLWhere; 119 CPLString osWFSWhere; 120 121 CPLString osTargetNamespace; 122 CPLString GetDescribeFeatureTypeURL(int bWithNS); 123 124 int nExpectedInserts; 125 CPLString osGlobalInsert; 126 std::vector<CPLString> aosFIDList; 127 128 int bInTransaction; 129 130 CPLString GetPostHeader(); 131 132 int bUseFeatureIdAtLayerLevel; 133 134 int bPagingActive; 135 int nPagingStartIndex; 136 int nFeatureRead; 137 int nFeatureCountRequested; 138 139 OGRFeatureDefn* BuildLayerDefnFromFeatureClass(GMLFeatureClass* poClass); 140 141 char *pszRequiredOutputFormat; 142 143 std::vector<OGRWFSSortDesc> aoSortColumns; 144 145 public: 146 OGRWFSLayer(OGRWFSDataSource* poDS, 147 OGRSpatialReference* poSRS, 148 int bAxisOrderAlreadyInverted, 149 const char* pszBaseURL, 150 const char* pszName, 151 const char* pszNS, 152 const char* pszNSVal); 153 154 ~OGRWFSLayer(); 155 156 OGRWFSLayer* Clone(); 157 158 GetName()159 const char *GetName() { return pszName; } 160 161 virtual void ResetReading(); 162 virtual OGRFeature* GetNextFeature(); 163 virtual OGRFeature* GetFeature(GIntBig nFID); 164 165 virtual OGRFeatureDefn * GetLayerDefn(); 166 167 virtual int TestCapability( const char * ); 168 169 virtual void SetSpatialFilter( OGRGeometry * ); 170 171 virtual OGRErr SetAttributeFilter( const char * ); 172 173 virtual GIntBig GetFeatureCount( int bForce = TRUE ); 174 175 void SetExtents(double dfMinX, double dfMinY, double dfMaxX, double dfMaxY); 176 virtual OGRErr GetExtent(OGREnvelope *psExtent, int bForce = TRUE); 177 178 virtual OGRErr ICreateFeature( OGRFeature *poFeature ); 179 virtual OGRErr ISetFeature( OGRFeature *poFeature ); 180 virtual OGRErr DeleteFeature( GIntBig nFID ); 181 182 virtual OGRErr StartTransaction(); 183 virtual OGRErr CommitTransaction(); 184 virtual OGRErr RollbackTransaction(); 185 HasLayerDefn()186 int HasLayerDefn() { return poFeatureDefn != NULL; } 187 188 OGRFeatureDefn* ParseSchema(CPLXMLNode* psSchema); 189 OGRFeatureDefn* BuildLayerDefn(OGRFeatureDefn* poSrcFDefn = NULL); 190 191 OGRErr DeleteFromFilter( CPLString osOGCFilter ); 192 GetLastInsertedFIDList()193 const std::vector<CPLString>& GetLastInsertedFIDList() { return aosFIDList; } 194 195 const char *GetShortName(); 196 197 void SetRequiredOutputFormat(const char* pszRequiredOutputFormatIn); 198 GetRequiredOutputFormat()199 const char *GetRequiredOutputFormat() { return pszRequiredOutputFormat; }; 200 201 void SetOrderBy(const std::vector<OGRWFSSortDesc>& aoSortColumnsIn); HasGotApproximateLayerDefn()202 int HasGotApproximateLayerDefn() { GetLayerDefn(); return bGotApproximateLayerDefn; } 203 GetNamespacePrefix()204 const char* GetNamespacePrefix() { return pszNS; } GetNamespaceName()205 const char* GetNamespaceName() { return pszNSVal; } 206 }; 207 208 /************************************************************************/ 209 /* OGRWFSJoinLayer */ 210 /************************************************************************/ 211 212 class OGRWFSJoinLayer : public OGRLayer 213 { 214 OGRWFSDataSource *poDS; 215 OGRFeatureDefn *poFeatureDefn; 216 217 CPLString osGlobalFilter; 218 CPLString osSortBy; 219 int bDistinct; 220 std::set<CPLString> aoSetMD5; 221 222 std::vector<OGRWFSLayer*> apoLayers; 223 224 GDALDataset *poBaseDS; 225 OGRLayer *poBaseLayer; 226 int bReloadNeeded; 227 int bHasFetched; 228 229 int bPagingActive; 230 int nPagingStartIndex; 231 int nFeatureRead; 232 int nFeatureCountRequested; 233 234 std::vector<CPLString> aoSrcFieldNames, aoSrcGeomFieldNames; 235 236 CPLString osFeatureTypes; 237 238 OGRWFSJoinLayer(OGRWFSDataSource* poDS, 239 const swq_select* psSelectInfo, 240 const CPLString& osGlobalFilter); 241 CPLString MakeGetFeatureURL(int bRequestHits = FALSE); 242 GDALDataset* FetchGetFeature(); 243 GIntBig ExecuteGetFeatureResultTypeHits(); 244 245 public: 246 247 static OGRWFSJoinLayer* Build(OGRWFSDataSource* poDS, 248 const swq_select* psSelectInfo); 249 ~OGRWFSJoinLayer(); 250 251 virtual void ResetReading(); 252 virtual OGRFeature* GetNextFeature(); 253 254 virtual OGRFeatureDefn * GetLayerDefn(); 255 256 virtual int TestCapability( const char * ); 257 258 virtual GIntBig GetFeatureCount( int bForce = TRUE ); 259 260 virtual void SetSpatialFilter( OGRGeometry * ); 261 262 virtual OGRErr SetAttributeFilter( const char * ); 263 }; 264 265 /************************************************************************/ 266 /* OGRWFSDataSource */ 267 /************************************************************************/ 268 269 class OGRWFSDataSource : public OGRDataSource 270 { 271 char* pszName; 272 int bRewriteFile; 273 CPLXMLNode* psFileXML; 274 275 OGRWFSLayer** papoLayers; 276 int nLayers; 277 std::map<OGRLayer*, OGRLayer*> oMap; 278 279 int bUpdate; 280 281 int bGetFeatureSupportHits; 282 CPLString osVersion; 283 int bNeedNAMESPACE; 284 int bHasMinOperators; 285 int bHasNullCheck; 286 int bPropertyIsNotEqualToSupported; 287 int bUseFeatureId; 288 int bGmlObjectIdNeedsGMLPrefix; 289 int bRequiresEnvelopeSpatialFilter; 290 int DetectRequiresEnvelopeSpatialFilter(CPLXMLNode* psRoot); 291 292 int bTransactionSupport; 293 char** papszIdGenMethods; 294 int DetectTransactionSupport(CPLXMLNode* psRoot); 295 296 CPLString osBaseURL; 297 CPLString osPostTransactionURL; 298 299 CPLXMLNode* LoadFromFile( const char * pszFilename ); 300 301 int bUseHttp10; 302 303 char** papszHttpOptions; 304 305 int bPagingAllowed; 306 int nPageSize; 307 int nBaseStartIndex; 308 int DetectSupportPagingWFS2(CPLXMLNode* psRoot); 309 310 int bStandardJoinsWFS2; 311 int DetectSupportStandardJoinsWFS2(CPLXMLNode* psRoot); 312 313 int bLoadMultipleLayerDefn; 314 std::set<CPLString> aoSetAlreadyTriedLayers; 315 316 CPLString osLayerMetadataCSV; 317 CPLString osLayerMetadataTmpFileName; 318 OGRDataSource *poLayerMetadataDS; 319 OGRLayer *poLayerMetadataLayer; 320 321 CPLString osGetCapabilities; 322 const char *apszGetCapabilities[2]; 323 GDALDataset *poLayerGetCapabilitiesDS; 324 OGRLayer *poLayerGetCapabilitiesLayer; 325 326 int bKeepLayerNamePrefix; 327 328 int bEmptyAsNull; 329 330 int bInvertAxisOrderIfLatLong; 331 CPLString osConsiderEPSGAsURN; 332 int bExposeGMLId; 333 334 CPLHTTPResult* SendGetCapabilities(const char* pszBaseURL, 335 CPLString& osTypeName); 336 337 int GetLayerIndex(const char* pszName); 338 339 public: 340 OGRWFSDataSource(); 341 ~OGRWFSDataSource(); 342 343 int Open( const char * pszFilename, 344 int bUpdate, 345 char** papszOpenOptions ); 346 GetName()347 virtual const char* GetName() { return pszName; } 348 GetLayerCount()349 virtual int GetLayerCount() { return nLayers; } 350 virtual OGRLayer* GetLayer( int ); 351 virtual OGRLayer* GetLayerByName(const char* pszLayerName); 352 353 virtual int TestCapability( const char * ); 354 355 virtual OGRLayer * ExecuteSQL( const char *pszSQLCommand, 356 OGRGeometry *poSpatialFilter, 357 const char *pszDialect ); 358 virtual void ReleaseResultSet( OGRLayer * poResultsSet ); 359 UpdateMode()360 int UpdateMode() { return bUpdate; } SupportTransactions()361 int SupportTransactions() { return bTransactionSupport; } DisableSupportHits()362 void DisableSupportHits() { bGetFeatureSupportHits = FALSE; } GetFeatureSupportHits()363 int GetFeatureSupportHits() { return bGetFeatureSupportHits; } GetVersion()364 const char *GetVersion() { return osVersion.c_str(); } 365 366 int IsOldDeegree(const char* pszErrorString); GetNeedNAMESPACE()367 int GetNeedNAMESPACE() { return bNeedNAMESPACE; } HasMinOperators()368 int HasMinOperators() { return bHasMinOperators; } HasNullCheck()369 int HasNullCheck() { return bHasNullCheck; } UseFeatureId()370 int UseFeatureId() { return bUseFeatureId; } RequiresEnvelopeSpatialFilter()371 int RequiresEnvelopeSpatialFilter() { return bRequiresEnvelopeSpatialFilter; } SetGmlObjectIdNeedsGMLPrefix()372 void SetGmlObjectIdNeedsGMLPrefix() { bGmlObjectIdNeedsGMLPrefix = TRUE; } DoesGmlObjectIdNeedGMLPrefix()373 int DoesGmlObjectIdNeedGMLPrefix() { return bGmlObjectIdNeedsGMLPrefix; } 374 SetPropertyIsNotEqualToUnSupported()375 void SetPropertyIsNotEqualToUnSupported() { bPropertyIsNotEqualToSupported = FALSE; } PropertyIsNotEqualToSupported()376 int PropertyIsNotEqualToSupported() { return bPropertyIsNotEqualToSupported; } 377 378 CPLString GetPostTransactionURL(); 379 380 void SaveLayerSchema(const char* pszLayerName, CPLXMLNode* psSchema); 381 382 CPLHTTPResult* HTTPFetch( const char* pszURL, char** papszOptions ); 383 IsPagingAllowed()384 int IsPagingAllowed() const { return bPagingAllowed; } GetPageSize()385 int GetPageSize() const { return nPageSize; } GetBaseStartIndex()386 int GetBaseStartIndex() const { return nBaseStartIndex; } 387 388 void LoadMultipleLayerDefn(const char* pszLayerName, 389 char* pszNS, char* pszNSVal); 390 GetKeepLayerNamePrefix()391 int GetKeepLayerNamePrefix() { return bKeepLayerNamePrefix; } GetBaseURL()392 const CPLString& GetBaseURL() { return osBaseURL; } 393 IsEmptyAsNull()394 int IsEmptyAsNull() const { return bEmptyAsNull; } InvertAxisOrderIfLatLong()395 int InvertAxisOrderIfLatLong() const { return bInvertAxisOrderIfLatLong; } GetConsiderEPSGAsURN()396 const CPLString& GetConsiderEPSGAsURN() const { return osConsiderEPSGAsURN; } 397 ExposeGMLId()398 int ExposeGMLId() const { return bExposeGMLId; } 399 400 virtual char** GetMetadataDomainList(); 401 virtual char** GetMetadata( const char * pszDomain = "" ); 402 }; 403 404 #endif /* ndef _OGR_WFS_H_INCLUDED */ 405