LCOV - code coverage report
Current view: top level - ogr/ogrsf_frmts/generic - ogreditablelayer.cpp (source / functions) Hit Total Coverage
Test: gdal_filtered.info Lines: 364 403 90.3 %
Date: 2024-11-21 22:18:42 Functions: 41 45 91.1 %

          Line data    Source code
       1             : /******************************************************************************
       2             :  *
       3             :  * Project:  OpenGIS Simple Features Reference Implementation
       4             :  * Purpose:  Implements OGREditableLayer class
       5             :  * Author:   Even Rouault <even.rouault at spatialys.com>
       6             :  *
       7             :  ******************************************************************************
       8             :  * Copyright (c) 2015, Even Rouault <even.rouault at spatialys.com>
       9             :  *
      10             :  * SPDX-License-Identifier: MIT
      11             :  ****************************************************************************/
      12             : 
      13             : #include "ogreditablelayer.h"
      14             : #include "../mem/ogr_mem.h"
      15             : 
      16             : #include <map>
      17             : 
      18             : //! @cond Doxygen_Suppress
      19             : 
      20             : /************************************************************************/
      21             : /*                  ~IOGREditableLayerSynchronizer()                    */
      22             : /************************************************************************/
      23             : 
      24         371 : IOGREditableLayerSynchronizer::~IOGREditableLayerSynchronizer()
      25             : {
      26         371 : }
      27             : 
      28             : /************************************************************************/
      29             : /*                          OGREditableLayer()                          */
      30             : /************************************************************************/
      31             : 
      32         371 : OGREditableLayer::OGREditableLayer(
      33             :     OGRLayer *poDecoratedLayer, bool bTakeOwnershipDecoratedLayer,
      34             :     IOGREditableLayerSynchronizer *poSynchronizer,
      35         371 :     bool bTakeOwnershipSynchronizer)
      36             :     : OGRLayerDecorator(poDecoratedLayer, bTakeOwnershipDecoratedLayer),
      37             :       m_poSynchronizer(poSynchronizer),
      38             :       m_bTakeOwnershipSynchronizer(bTakeOwnershipSynchronizer),
      39         371 :       m_poEditableFeatureDefn(poDecoratedLayer->GetLayerDefn()->Clone()),
      40         371 :       m_nNextFID(0), m_poMemLayer(new OGRMemLayer("", nullptr, wkbNone)),
      41             :       m_bStructureModified(false), m_bSupportsCreateGeomField(false),
      42        1113 :       m_bSupportsCurveGeometries(false)
      43             : {
      44         371 :     m_poEditableFeatureDefn->Reference();
      45             : 
      46        1348 :     for (int i = 0; i < m_poEditableFeatureDefn->GetFieldCount(); i++)
      47         977 :         m_poMemLayer->CreateField(m_poEditableFeatureDefn->GetFieldDefn(i));
      48             : 
      49         549 :     for (int i = 0; i < m_poEditableFeatureDefn->GetGeomFieldCount(); i++)
      50         356 :         m_poMemLayer->CreateGeomField(
      51         178 :             m_poEditableFeatureDefn->GetGeomFieldDefn(i));
      52             : 
      53         371 :     m_oIter = m_oSetCreated.begin();
      54         371 : }
      55             : 
      56             : /************************************************************************/
      57             : /*                         ~OGREditableLayer()                          */
      58             : /************************************************************************/
      59             : 
      60         371 : OGREditableLayer::~OGREditableLayer()
      61             : {
      62         371 :     OGREditableLayer::SyncToDisk();
      63             : 
      64         371 :     m_poEditableFeatureDefn->Release();
      65         371 :     delete m_poMemLayer;
      66         371 :     if (m_bTakeOwnershipSynchronizer)
      67         371 :         delete m_poSynchronizer;
      68         371 : }
      69             : 
      70             : /************************************************************************/
      71             : /*                           SetNextFID()                               */
      72             : /************************************************************************/
      73             : 
      74           3 : void OGREditableLayer::SetNextFID(GIntBig nNextFID)
      75             : {
      76           3 :     m_nNextFID = nNextFID;
      77           3 : }
      78             : 
      79             : /************************************************************************/
      80             : /*                       SetSupportsCurveGeometries()                   */
      81             : /************************************************************************/
      82             : 
      83         208 : void OGREditableLayer::SetSupportsCurveGeometries(bool bSupportsCurveGeometries)
      84             : {
      85         208 :     m_bSupportsCurveGeometries = bSupportsCurveGeometries;
      86         208 : }
      87             : 
      88             : /************************************************************************/
      89             : /*                       SetSupportsCreateGeomField()                   */
      90             : /************************************************************************/
      91             : 
      92         208 : void OGREditableLayer::SetSupportsCreateGeomField(bool bSupportsCreateGeomField)
      93             : {
      94         208 :     m_bSupportsCreateGeomField = bSupportsCreateGeomField;
      95         208 : }
      96             : 
      97             : /************************************************************************/
      98             : /*                           DetectNextFID()                            */
      99             : /************************************************************************/
     100             : 
     101           6 : void OGREditableLayer::DetectNextFID()
     102             : {
     103           6 :     if (m_nNextFID > 0)
     104           1 :         return;
     105           5 :     m_nNextFID = 0;
     106           5 :     m_poDecoratedLayer->ResetReading();
     107           5 :     OGRFeature *poFeat = nullptr;
     108          26 :     while ((poFeat = m_poDecoratedLayer->GetNextFeature()) != nullptr)
     109             :     {
     110          21 :         if (poFeat->GetFID() > m_nNextFID)
     111          20 :             m_nNextFID = poFeat->GetFID();
     112          21 :         delete poFeat;
     113             :     }
     114           5 :     m_nNextFID++;
     115             : }
     116             : 
     117             : /************************************************************************/
     118             : /*                         GetSrcGeomFieldIndex()                       */
     119             : /************************************************************************/
     120             : 
     121         176 : int OGREditableLayer::GetSrcGeomFieldIndex(int iGeomField)
     122             : {
     123         347 :     if (m_poDecoratedLayer == nullptr || iGeomField < 0 ||
     124         171 :         iGeomField >= m_poEditableFeatureDefn->GetGeomFieldCount())
     125             :     {
     126          21 :         return -1;
     127             :     }
     128             :     OGRGeomFieldDefn *poGeomFieldDefn =
     129         155 :         m_poEditableFeatureDefn->GetGeomFieldDefn(iGeomField);
     130         310 :     return m_poDecoratedLayer->GetLayerDefn()->GetGeomFieldIndex(
     131         155 :         poGeomFieldDefn->GetNameRef());
     132             : }
     133             : 
     134             : /************************************************************************/
     135             : /*                            ResetReading()                            */
     136             : /************************************************************************/
     137             : 
     138         550 : void OGREditableLayer::ResetReading()
     139             : {
     140         550 :     if (!m_poDecoratedLayer)
     141           0 :         return;
     142         550 :     m_poDecoratedLayer->ResetReading();
     143         550 :     m_oIter = m_oSetCreated.begin();
     144             : }
     145             : 
     146             : /************************************************************************/
     147             : /*                             Translate()                              */
     148             : /************************************************************************/
     149             : 
     150        1236 : OGRFeature *OGREditableLayer::Translate(OGRFeatureDefn *poTargetDefn,
     151             :                                         OGRFeature *poSrcFeature,
     152             :                                         bool bCanStealSrcFeature,
     153             :                                         bool bHideDeletedFields)
     154             : {
     155        1236 :     if (poSrcFeature == nullptr)
     156          20 :         return nullptr;
     157        1216 :     OGRFeature *poRet = new OGRFeature(poTargetDefn);
     158             : 
     159        1216 :     std::map<CPLString, int> oMapTargetFieldNameToIdx;
     160        1216 :     std::map<CPLString, int> *poMap = &oMapTargetFieldNameToIdx;
     161        2031 :     if (poTargetDefn == m_poEditableFeatureDefn &&
     162         815 :         !m_oMapEditableFDefnFieldNameToIdx.empty())
     163             :     {
     164         677 :         poMap = &m_oMapEditableFDefnFieldNameToIdx;
     165             :     }
     166             :     else
     167             :     {
     168        3448 :         for (int iField = 0; iField < poTargetDefn->GetFieldCount(); iField++)
     169             :         {
     170        2909 :             oMapTargetFieldNameToIdx[poTargetDefn->GetFieldDefn(iField)
     171        2909 :                                          ->GetNameRef()] = iField;
     172             :         }
     173         539 :         if (poTargetDefn == m_poEditableFeatureDefn)
     174             :         {
     175             :             m_oMapEditableFDefnFieldNameToIdx =
     176         138 :                 std::move(oMapTargetFieldNameToIdx);
     177         138 :             poMap = &m_oMapEditableFDefnFieldNameToIdx;
     178             :         }
     179             :     }
     180             : 
     181             :     int *panMap = static_cast<int *>(
     182        1216 :         CPLMalloc(sizeof(int) * poSrcFeature->GetFieldCount()));
     183       10849 :     for (int iField = 0; iField < poSrcFeature->GetFieldCount(); iField++)
     184             :     {
     185             :         const char *pszFieldName =
     186        9633 :             poSrcFeature->GetFieldDefnRef(iField)->GetNameRef();
     187       16652 :         if (bHideDeletedFields &&
     188       16652 :             m_oSetDeletedFields.find(pszFieldName) != m_oSetDeletedFields.end())
     189             :         {
     190           7 :             panMap[iField] = -1;
     191             :         }
     192             :         else
     193             :         {
     194        9626 :             auto oIter = poMap->find(pszFieldName);
     195        9626 :             panMap[iField] = (oIter == poMap->end()) ? -1 : oIter->second;
     196             :         }
     197             :     }
     198        1216 :     poRet->SetFieldsFrom(poSrcFeature, panMap, TRUE);
     199        1216 :     CPLFree(panMap);
     200             : 
     201        2156 :     for (int i = 0; i < poTargetDefn->GetGeomFieldCount(); i++)
     202             :     {
     203         940 :         OGRGeomFieldDefn *poGeomField = poTargetDefn->GetGeomFieldDefn(i);
     204             :         int iSrcGeomFieldIdx =
     205         940 :             poTargetDefn->GetGeomFieldIndex(poGeomField->GetNameRef());
     206         940 :         if (iSrcGeomFieldIdx >= 0)
     207             :         {
     208         940 :             if (bCanStealSrcFeature)
     209             :             {
     210         730 :                 poRet->SetGeomFieldDirectly(
     211             :                     i, poSrcFeature->StealGeometry(iSrcGeomFieldIdx));
     212             :             }
     213             :             else
     214             :             {
     215         210 :                 poRet->SetGeomField(
     216         210 :                     i, poSrcFeature->GetGeomFieldRef(iSrcGeomFieldIdx));
     217             :             }
     218         940 :             OGRGeometry *poGeom = poRet->GetGeomFieldRef(i);
     219         940 :             if (poGeom != nullptr)
     220         870 :                 poGeom->assignSpatialReference(poGeomField->GetSpatialRef());
     221             :         }
     222             :     }
     223        1216 :     poRet->SetStyleString(poSrcFeature->GetStyleString());
     224        1216 :     poRet->SetNativeData(poSrcFeature->GetNativeData());
     225        1216 :     poRet->SetNativeMediaType(poSrcFeature->GetNativeMediaType());
     226        1216 :     poRet->SetFID(poSrcFeature->GetFID());
     227             : 
     228        1216 :     return poRet;
     229             : }
     230             : 
     231             : /************************************************************************/
     232             : /*                           GetNextFeature()                           */
     233             : /************************************************************************/
     234             : 
     235         774 : OGRFeature *OGREditableLayer::GetNextFeature()
     236             : {
     237         774 :     if (!m_poDecoratedLayer)
     238           0 :         return nullptr;
     239             :     while (true)
     240             :     {
     241         927 :         OGRFeature *poSrcFeature = m_poDecoratedLayer->GetNextFeature();
     242         927 :         bool bHideDeletedFields = true;
     243         927 :         if (poSrcFeature != nullptr)
     244             :         {
     245         746 :             const GIntBig nFID = poSrcFeature->GetFID();
     246         746 :             if (m_oSetDeleted.find(nFID) != m_oSetDeleted.end())
     247             :             {
     248           6 :                 delete poSrcFeature;
     249           6 :                 continue;
     250             :             }
     251        1469 :             else if (m_oSetCreated.find(nFID) != m_oSetCreated.end() ||
     252        1469 :                      m_oSetEdited.find(nFID) != m_oSetEdited.end())
     253             :             {
     254          48 :                 delete poSrcFeature;
     255          48 :                 poSrcFeature = m_poMemLayer->GetFeature(nFID);
     256          48 :                 bHideDeletedFields = false;
     257             :             }
     258             :         }
     259             :         else
     260             :         {
     261         181 :             if (m_oIter != m_oSetCreated.end())
     262             :             {
     263          17 :                 poSrcFeature = m_poMemLayer->GetFeature(*m_oIter);
     264          17 :                 bHideDeletedFields = false;
     265          17 :                 ++m_oIter;
     266             :             }
     267             :             else
     268             :             {
     269         164 :                 return nullptr;
     270             :             }
     271             :         }
     272         757 :         OGRFeature *poRet = Translate(m_poEditableFeatureDefn, poSrcFeature,
     273             :                                       true, bHideDeletedFields);
     274         757 :         delete poSrcFeature;
     275             : 
     276        1650 :         if ((m_poFilterGeom == nullptr ||
     277        1512 :              FilterGeometry(poRet->GetGeomFieldRef(m_iGeomFieldFilter))) &&
     278         755 :             (m_poAttrQuery == nullptr || m_poAttrQuery->Evaluate(poRet)))
     279             :         {
     280         610 :             return poRet;
     281             :         }
     282         147 :         delete poRet;
     283         153 :     }
     284             : }
     285             : 
     286             : /************************************************************************/
     287             : /*                          SetNextByIndex()                            */
     288             : /************************************************************************/
     289             : 
     290          18 : OGRErr OGREditableLayer::SetNextByIndex(GIntBig nIndex)
     291             : {
     292          31 :     if (m_poDecoratedLayer != nullptr && m_oSetCreated.empty() &&
     293          49 :         m_oSetDeleted.empty() && m_oSetEdited.empty())
     294             :     {
     295          13 :         return m_poDecoratedLayer->SetNextByIndex(nIndex);
     296             :     }
     297             : 
     298           5 :     return OGRLayer::SetNextByIndex(nIndex);
     299             : }
     300             : 
     301             : /************************************************************************/
     302             : /*                              GetFeature()                            */
     303             : /************************************************************************/
     304             : 
     305          78 : OGRFeature *OGREditableLayer::GetFeature(GIntBig nFID)
     306             : {
     307          78 :     if (!m_poDecoratedLayer)
     308           0 :         return nullptr;
     309             : 
     310          78 :     OGRFeature *poSrcFeature = nullptr;
     311          78 :     bool bHideDeletedFields = true;
     312         151 :     if (m_oSetCreated.find(nFID) != m_oSetCreated.end() ||
     313         151 :         m_oSetEdited.find(nFID) != m_oSetEdited.end())
     314             :     {
     315          20 :         poSrcFeature = m_poMemLayer->GetFeature(nFID);
     316          20 :         bHideDeletedFields = false;
     317             :     }
     318          58 :     else if (m_oSetDeleted.find(nFID) != m_oSetDeleted.end())
     319             :     {
     320           4 :         poSrcFeature = nullptr;
     321             :     }
     322             :     else
     323             :     {
     324          54 :         poSrcFeature = m_poDecoratedLayer->GetFeature(nFID);
     325             :     }
     326          78 :     OGRFeature *poRet = Translate(m_poEditableFeatureDefn, poSrcFeature, true,
     327             :                                   bHideDeletedFields);
     328          78 :     delete poSrcFeature;
     329          78 :     return poRet;
     330             : }
     331             : 
     332             : /************************************************************************/
     333             : /*                            ISetFeature()                             */
     334             : /************************************************************************/
     335             : 
     336          27 : OGRErr OGREditableLayer::ISetFeature(OGRFeature *poFeature)
     337             : {
     338          27 :     if (!m_poDecoratedLayer)
     339           0 :         return OGRERR_FAILURE;
     340             : 
     341          40 :     if (!m_bStructureModified && m_oSetDeleted.empty() &&
     342          74 :         m_oSetEdited.empty() && m_oSetCreated.empty() &&
     343           7 :         m_poDecoratedLayer->TestCapability(OLCRandomWrite))
     344             :     {
     345           0 :         OGRFeature *poTargetFeature = Translate(
     346           0 :             m_poDecoratedLayer->GetLayerDefn(), poFeature, false, false);
     347           0 :         OGRErr eErr = m_poDecoratedLayer->SetFeature(poTargetFeature);
     348           0 :         delete poTargetFeature;
     349           0 :         return eErr;
     350             :     }
     351             : 
     352             :     OGRFeature *poMemFeature =
     353          27 :         Translate(m_poMemLayer->GetLayerDefn(), poFeature, false, false);
     354          27 :     OGRErr eErr = m_poMemLayer->SetFeature(poMemFeature);
     355          27 :     if (eErr == OGRERR_NONE)
     356             :     {
     357          23 :         const GIntBig nFID = poMemFeature->GetFID();
     358          23 :         m_oSetDeleted.erase(nFID);
     359             :         // If the feature isn't in the created list, insert it in the edited
     360             :         // list
     361          23 :         if (m_oSetCreated.find(nFID) == m_oSetCreated.end())
     362             :         {
     363          21 :             m_oSetEdited.insert(nFID);
     364             :         }
     365          23 :         poFeature->SetFID(nFID);
     366             :     }
     367          27 :     delete poMemFeature;
     368             : 
     369          27 :     return eErr;
     370             : }
     371             : 
     372             : /************************************************************************/
     373             : /*                          ICreateFeature()                            */
     374             : /************************************************************************/
     375             : 
     376         374 : OGRErr OGREditableLayer::ICreateFeature(OGRFeature *poFeature)
     377             : {
     378         374 :     if (!m_poDecoratedLayer)
     379           0 :         return OGRERR_FAILURE;
     380             : 
     381         740 :     if (!m_bStructureModified && m_oSetDeleted.empty() &&
     382        1114 :         m_oSetCreated.empty() &&
     383         369 :         m_poDecoratedLayer->TestCapability(OLCSequentialWrite))
     384             :     {
     385         368 :         OGRFeature *poTargetFeature = Translate(
     386         368 :             m_poDecoratedLayer->GetLayerDefn(), poFeature, false, false);
     387         368 :         OGRErr eErr = m_poDecoratedLayer->CreateFeature(poTargetFeature);
     388         368 :         if (poFeature->GetFID() < 0)
     389         358 :             poFeature->SetFID(poTargetFeature->GetFID());
     390         368 :         delete poTargetFeature;
     391         368 :         return eErr;
     392             :     }
     393             : 
     394             :     OGRFeature *poMemFeature =
     395           6 :         Translate(m_poMemLayer->GetLayerDefn(), poFeature, false, false);
     396           6 :     DetectNextFID();
     397           6 :     if (poMemFeature->GetFID() < 0)
     398           4 :         poMemFeature->SetFID(m_nNextFID++);
     399           6 :     OGRErr eErr = m_poMemLayer->CreateFeature(poMemFeature);
     400           6 :     if (eErr == OGRERR_NONE)
     401             :     {
     402           6 :         const GIntBig nFID = poMemFeature->GetFID();
     403           6 :         m_oSetDeleted.erase(nFID);
     404           6 :         m_oSetEdited.erase(nFID);
     405           6 :         m_oSetCreated.insert(nFID);
     406           6 :         poFeature->SetFID(nFID);
     407             :     }
     408           6 :     delete poMemFeature;
     409             : 
     410           6 :     ResetReading();
     411             : 
     412           6 :     return eErr;
     413             : }
     414             : 
     415             : /************************************************************************/
     416             : /*                          IUpsertFeature()                            */
     417             : /************************************************************************/
     418             : 
     419           0 : OGRErr OGREditableLayer::IUpsertFeature(OGRFeature *poFeature)
     420             : {
     421             :     auto poFeatureExisting =
     422           0 :         std::unique_ptr<OGRFeature>(GetFeature(poFeature->GetFID()));
     423           0 :     if (poFeatureExisting)
     424             :     {
     425           0 :         return ISetFeature(poFeature);
     426             :     }
     427             :     else
     428             :     {
     429           0 :         return ICreateFeature(poFeature);
     430             :     }
     431             : }
     432             : 
     433             : /************************************************************************/
     434             : /*                            IUpdateFeature()                          */
     435             : /************************************************************************/
     436             : 
     437           6 : OGRErr OGREditableLayer::IUpdateFeature(OGRFeature *poFeature,
     438             :                                         int nUpdatedFieldsCount,
     439             :                                         const int *panUpdatedFieldsIdx,
     440             :                                         int nUpdatedGeomFieldsCount,
     441             :                                         const int *panUpdatedGeomFieldsIdx,
     442             :                                         bool bUpdateStyleString)
     443             : {
     444             :     // Do not use OGRLayerDecorator::IUpdateFeature() which will forward
     445             :     // to the decorated layer
     446           6 :     return OGRLayer::IUpdateFeature(
     447             :         poFeature, nUpdatedFieldsCount, panUpdatedFieldsIdx,
     448           6 :         nUpdatedGeomFieldsCount, panUpdatedGeomFieldsIdx, bUpdateStyleString);
     449             : }
     450             : 
     451             : /************************************************************************/
     452             : /*                          DeleteFeature()                             */
     453             : /************************************************************************/
     454             : 
     455          19 : OGRErr OGREditableLayer::DeleteFeature(GIntBig nFID)
     456             : {
     457          19 :     if (!m_poDecoratedLayer)
     458           0 :         return OGRERR_FAILURE;
     459             : 
     460             :     OGRErr eErr;
     461          19 :     if (m_oSetDeleted.find(nFID) != m_oSetDeleted.end())
     462             :     {
     463           3 :         eErr = OGRERR_NON_EXISTING_FEATURE;
     464             :     }
     465             :     // cppcheck-suppress redundantIfRemove
     466          16 :     else if (m_oSetCreated.find(nFID) != m_oSetCreated.end())
     467             :     {
     468           1 :         m_oSetCreated.erase(nFID);
     469           1 :         eErr = m_poMemLayer->DeleteFeature(nFID);
     470             :     }
     471             :     // cppcheck-suppress redundantIfRemove
     472          15 :     else if (m_oSetEdited.find(nFID) != m_oSetEdited.end())
     473             :     {
     474           1 :         m_oSetEdited.erase(nFID);
     475           1 :         m_oSetDeleted.insert(nFID);
     476           1 :         eErr = m_poMemLayer->DeleteFeature(nFID);
     477             :     }
     478             :     else
     479             :     {
     480          14 :         OGRFeature *poFeature = m_poDecoratedLayer->GetFeature(nFID);
     481          14 :         if (poFeature != nullptr)
     482             :         {
     483           5 :             m_oSetDeleted.insert(nFID);
     484           5 :             eErr = OGRERR_NONE;
     485           5 :             delete poFeature;
     486             :         }
     487             :         else
     488             :         {
     489           9 :             eErr = OGRERR_NON_EXISTING_FEATURE;
     490             :         }
     491             :     }
     492             : 
     493          19 :     ResetReading();
     494             : 
     495          19 :     return eErr;
     496             : }
     497             : 
     498             : /************************************************************************/
     499             : /*                             GetGeomType()                            */
     500             : /************************************************************************/
     501             : 
     502         244 : OGRwkbGeometryType OGREditableLayer::GetGeomType()
     503             : {
     504         244 :     return OGRLayer::GetGeomType();
     505             : }
     506             : 
     507             : /************************************************************************/
     508             : /*                             GetLayerDefn()                           */
     509             : /************************************************************************/
     510             : 
     511        2988 : OGRFeatureDefn *OGREditableLayer::GetLayerDefn()
     512             : {
     513        2988 :     return m_poEditableFeatureDefn;
     514             : }
     515             : 
     516             : /************************************************************************/
     517             : /*                             GetSpatialRef()                          */
     518             : /************************************************************************/
     519             : 
     520          73 : OGRSpatialReference *OGREditableLayer::GetSpatialRef()
     521             : {
     522          73 :     return OGRLayer::GetSpatialRef();
     523             : }
     524             : 
     525             : /************************************************************************/
     526             : /*                           GetSpatialFilter()                         */
     527             : /************************************************************************/
     528             : 
     529          19 : OGRGeometry *OGREditableLayer::GetSpatialFilter()
     530             : {
     531          19 :     return OGRLayer::GetSpatialFilter();
     532             : }
     533             : 
     534             : /************************************************************************/
     535             : /*                           SetAttributeFilter()                       */
     536             : /************************************************************************/
     537             : 
     538         219 : OGRErr OGREditableLayer::SetAttributeFilter(const char *poAttrFilter)
     539             : {
     540         219 :     return OGRLayer::SetAttributeFilter(poAttrFilter);
     541             : }
     542             : 
     543             : /************************************************************************/
     544             : /*                           GetArrowStream()                           */
     545             : /************************************************************************/
     546             : 
     547          24 : bool OGREditableLayer::GetArrowStream(struct ArrowArrayStream *out_stream,
     548             :                                       CSLConstList papszOptions)
     549             : {
     550          24 :     return OGRLayer::GetArrowStream(out_stream, papszOptions);
     551             : }
     552             : 
     553             : /************************************************************************/
     554             : /*                           SetSpatialFilter()                         */
     555             : /************************************************************************/
     556             : 
     557          86 : void OGREditableLayer::SetSpatialFilter(OGRGeometry *poGeom)
     558             : {
     559          86 :     SetSpatialFilter(0, poGeom);
     560          86 : }
     561             : 
     562             : /************************************************************************/
     563             : /*                           SetSpatialFilter()                         */
     564             : /************************************************************************/
     565             : 
     566         159 : void OGREditableLayer::SetSpatialFilter(int iGeomField, OGRGeometry *poGeom)
     567             : {
     568         169 :     if (iGeomField < 0 ||
     569          10 :         (iGeomField != 0 && iGeomField >= GetLayerDefn()->GetGeomFieldCount()))
     570             :     {
     571          10 :         CPLError(CE_Failure, CPLE_AppDefined,
     572             :                  "Invalid geometry field index : %d", iGeomField);
     573          10 :         return;
     574             :     }
     575             : 
     576         149 :     m_iGeomFieldFilter = iGeomField;
     577         149 :     if (InstallFilter(poGeom))
     578          50 :         ResetReading();
     579             : 
     580         149 :     int iSrcGeomFieldIdx = GetSrcGeomFieldIndex(iGeomField);
     581         149 :     if (iSrcGeomFieldIdx >= 0)
     582             :     {
     583         137 :         m_poDecoratedLayer->SetSpatialFilter(iSrcGeomFieldIdx, poGeom);
     584             :     }
     585         149 :     m_poMemLayer->SetSpatialFilter(iGeomField, poGeom);
     586             : }
     587             : 
     588             : /************************************************************************/
     589             : /*                         SetSpatialFilterRect()                       */
     590             : /************************************************************************/
     591             : 
     592           1 : void OGREditableLayer::SetSpatialFilterRect(double dfMinX, double dfMinY,
     593             :                                             double dfMaxX, double dfMaxY)
     594             : {
     595           1 :     return OGRLayer::SetSpatialFilterRect(dfMinX, dfMinY, dfMaxX, dfMaxY);
     596             : }
     597             : 
     598             : /************************************************************************/
     599             : /*                         SetSpatialFilterRect()                       */
     600             : /************************************************************************/
     601             : 
     602           2 : void OGREditableLayer::SetSpatialFilterRect(int iGeomField, double dfMinX,
     603             :                                             double dfMinY, double dfMaxX,
     604             :                                             double dfMaxY)
     605             : {
     606           2 :     return OGRLayer::SetSpatialFilterRect(iGeomField, dfMinX, dfMinY, dfMaxX,
     607           2 :                                           dfMaxY);
     608             : }
     609             : 
     610             : /************************************************************************/
     611             : /*                          GetFeatureCount()                           */
     612             : /************************************************************************/
     613             : 
     614         149 : GIntBig OGREditableLayer::GetFeatureCount(int bForce)
     615             : {
     616         149 :     if (!m_poDecoratedLayer)
     617           0 :         return 0;
     618         250 :     if (m_poAttrQuery == nullptr && m_poFilterGeom == nullptr &&
     619         399 :         m_oSetDeleted.empty() && m_oSetEdited.empty())
     620             :     {
     621         114 :         GIntBig nFC = m_poDecoratedLayer->GetFeatureCount(bForce);
     622         114 :         if (nFC >= 0)
     623             :         {
     624         114 :             nFC += m_oSetCreated.size();
     625             :         }
     626         114 :         return nFC;
     627             :     }
     628          35 :     return OGRLayer::GetFeatureCount(bForce);
     629             : }
     630             : 
     631             : /************************************************************************/
     632             : /*                             GetExtent()                              */
     633             : /************************************************************************/
     634             : 
     635           6 : OGRErr OGREditableLayer::GetExtent(OGREnvelope *psExtent, int bForce)
     636             : {
     637           6 :     return GetExtent(0, psExtent, bForce);
     638             : }
     639             : 
     640             : /************************************************************************/
     641             : /*                               GetExtent()                            */
     642             : /************************************************************************/
     643             : 
     644          27 : OGRErr OGREditableLayer::GetExtent(int iGeomField, OGREnvelope *psExtent,
     645             :                                    int bForce)
     646             : {
     647          27 :     if (!m_poDecoratedLayer)
     648           0 :         return OGRERR_FAILURE;
     649          27 :     int iSrcGeomFieldIdx = GetSrcGeomFieldIndex(iGeomField);
     650          27 :     if (iSrcGeomFieldIdx >= 0 && m_oSetEdited.empty() && m_oSetDeleted.empty())
     651             :     {
     652             :         OGRErr eErr =
     653          18 :             m_poDecoratedLayer->GetExtent(iSrcGeomFieldIdx, psExtent, bForce);
     654          18 :         if (eErr == OGRERR_NONE)
     655             :         {
     656          17 :             OGREnvelope sExtentMemLayer;
     657          17 :             if (m_poMemLayer->GetExtent(iGeomField, &sExtentMemLayer, bForce) ==
     658             :                 OGRERR_NONE)
     659             :             {
     660           1 :                 psExtent->Merge(sExtentMemLayer);
     661             :             }
     662             :         }
     663          18 :         return eErr;
     664             :     }
     665           9 :     return GetExtentInternal(iGeomField, psExtent, bForce);
     666             : }
     667             : 
     668             : /************************************************************************/
     669             : /*                            TestCapability()                          */
     670             : /************************************************************************/
     671             : 
     672         690 : int OGREditableLayer::TestCapability(const char *pszCap)
     673             : {
     674         690 :     if (!m_poDecoratedLayer)
     675           0 :         return FALSE;
     676         690 :     if (EQUAL(pszCap, OLCSequentialWrite) || EQUAL(pszCap, OLCRandomWrite) ||
     677         641 :         EQUAL(pszCap, OLCCreateField) || EQUAL(pszCap, OLCDeleteField) ||
     678         592 :         EQUAL(pszCap, OLCReorderFields) || EQUAL(pszCap, OLCAlterFieldDefn) ||
     679         576 :         EQUAL(pszCap, OLCAlterGeomFieldDefn) || EQUAL(pszCap, OLCDeleteFeature))
     680             :     {
     681         176 :         return m_poDecoratedLayer->TestCapability(OLCCreateField) == TRUE ||
     682         176 :                m_poDecoratedLayer->TestCapability(OLCSequentialWrite) == TRUE;
     683             :     }
     684         570 :     if (EQUAL(pszCap, OLCCreateGeomField))
     685           1 :         return m_bSupportsCreateGeomField;
     686         569 :     if (EQUAL(pszCap, OLCCurveGeometries))
     687         226 :         return m_bSupportsCurveGeometries;
     688         343 :     if (EQUAL(pszCap, OLCTransactions))
     689           8 :         return FALSE;
     690             : 
     691         335 :     return m_poDecoratedLayer->TestCapability(pszCap);
     692             : }
     693             : 
     694             : /************************************************************************/
     695             : /*                            CreateField()                             */
     696             : /************************************************************************/
     697             : 
     698         605 : OGRErr OGREditableLayer::CreateField(const OGRFieldDefn *poField, int bApproxOK)
     699             : {
     700         605 :     if (!m_poDecoratedLayer)
     701           0 :         return OGRERR_FAILURE;
     702             : 
     703         605 :     m_oMapEditableFDefnFieldNameToIdx.clear();
     704             : 
     705        1209 :     if (!m_bStructureModified &&
     706         604 :         m_poDecoratedLayer->TestCapability(OLCCreateField))
     707             :     {
     708         602 :         OGRErr eErr = m_poDecoratedLayer->CreateField(poField, bApproxOK);
     709         602 :         if (eErr == OGRERR_NONE)
     710             :         {
     711         602 :             eErr = m_poMemLayer->CreateField(poField, bApproxOK);
     712         602 :             if (eErr == OGRERR_NONE)
     713             :             {
     714         602 :                 m_poEditableFeatureDefn->AddFieldDefn(poField);
     715             :             }
     716             :         }
     717         602 :         return eErr;
     718             :     }
     719             : 
     720           3 :     OGRErr eErr = m_poMemLayer->CreateField(poField, bApproxOK);
     721           3 :     if (eErr == OGRERR_NONE)
     722             :     {
     723           3 :         m_poEditableFeatureDefn->AddFieldDefn(poField);
     724           3 :         m_bStructureModified = true;
     725             :     }
     726           3 :     return eErr;
     727             : }
     728             : 
     729             : /************************************************************************/
     730             : /*                             DeleteField()                            */
     731             : /************************************************************************/
     732             : 
     733           4 : OGRErr OGREditableLayer::DeleteField(int iField)
     734             : {
     735           4 :     if (!m_poDecoratedLayer)
     736           0 :         return OGRERR_FAILURE;
     737             : 
     738           4 :     m_oMapEditableFDefnFieldNameToIdx.clear();
     739             : 
     740           4 :     CPLString osDeletedField;
     741           4 :     if (iField >= 0 && iField < m_poEditableFeatureDefn->GetFieldCount())
     742             :     {
     743             :         osDeletedField =
     744           3 :             m_poEditableFeatureDefn->GetFieldDefn(iField)->GetNameRef();
     745             :     }
     746             : 
     747           4 :     OGRErr eErr = m_poMemLayer->DeleteField(iField);
     748           4 :     if (eErr == OGRERR_NONE)
     749             :     {
     750           3 :         m_poEditableFeatureDefn->DeleteFieldDefn(iField);
     751           3 :         m_bStructureModified = true;
     752           3 :         m_oSetDeletedFields.insert(osDeletedField);
     753             :     }
     754           4 :     return eErr;
     755             : }
     756             : 
     757             : /************************************************************************/
     758             : /*                             ReorderFields()                          */
     759             : /************************************************************************/
     760             : 
     761           2 : OGRErr OGREditableLayer::ReorderFields(int *panMap)
     762             : {
     763           2 :     if (!m_poDecoratedLayer)
     764           0 :         return OGRERR_FAILURE;
     765             : 
     766           2 :     m_oMapEditableFDefnFieldNameToIdx.clear();
     767             : 
     768           2 :     OGRErr eErr = m_poMemLayer->ReorderFields(panMap);
     769           2 :     if (eErr == OGRERR_NONE)
     770             :     {
     771           1 :         m_poEditableFeatureDefn->ReorderFieldDefns(panMap);
     772           1 :         m_bStructureModified = true;
     773             :     }
     774           2 :     return eErr;
     775             : }
     776             : 
     777             : /************************************************************************/
     778             : /*                            AlterFieldDefn()                          */
     779             : /************************************************************************/
     780             : 
     781           2 : OGRErr OGREditableLayer::AlterFieldDefn(int iField,
     782             :                                         OGRFieldDefn *poNewFieldDefn,
     783             :                                         int nFlagsIn)
     784             : {
     785           2 :     if (!m_poDecoratedLayer)
     786           0 :         return OGRERR_FAILURE;
     787             : 
     788           2 :     m_oMapEditableFDefnFieldNameToIdx.clear();
     789             : 
     790             :     OGRErr eErr =
     791           2 :         m_poMemLayer->AlterFieldDefn(iField, poNewFieldDefn, nFlagsIn);
     792           2 :     if (eErr == OGRERR_NONE)
     793             :     {
     794             :         OGRFieldDefn *poFieldDefn =
     795           1 :             m_poEditableFeatureDefn->GetFieldDefn(iField);
     796             :         OGRFieldDefn *poMemFieldDefn =
     797           1 :             m_poMemLayer->GetLayerDefn()->GetFieldDefn(iField);
     798           1 :         poFieldDefn->SetName(poMemFieldDefn->GetNameRef());
     799           1 :         poFieldDefn->SetType(poMemFieldDefn->GetType());
     800           1 :         poFieldDefn->SetSubType(poMemFieldDefn->GetSubType());
     801           1 :         poFieldDefn->SetWidth(poMemFieldDefn->GetWidth());
     802           1 :         poFieldDefn->SetPrecision(poMemFieldDefn->GetPrecision());
     803           1 :         poFieldDefn->SetDefault(poMemFieldDefn->GetDefault());
     804           1 :         poFieldDefn->SetNullable(poMemFieldDefn->IsNullable());
     805           1 :         poFieldDefn->SetUnique(poMemFieldDefn->IsUnique());
     806           1 :         poFieldDefn->SetDomainName(poMemFieldDefn->GetDomainName());
     807           1 :         poFieldDefn->SetComment(poMemFieldDefn->GetComment());
     808           1 :         m_bStructureModified = true;
     809             :     }
     810           2 :     return eErr;
     811             : }
     812             : 
     813             : /************************************************************************/
     814             : /*                         AlterGeomFieldDefn()                         */
     815             : /************************************************************************/
     816             : 
     817           0 : OGRErr OGREditableLayer::AlterGeomFieldDefn(
     818             :     int iGeomField, const OGRGeomFieldDefn *poNewGeomFieldDefn, int nFlagsIn)
     819             : {
     820           0 :     if (!m_poDecoratedLayer)
     821           0 :         return OGRERR_FAILURE;
     822             : 
     823           0 :     OGRErr eErr = m_poMemLayer->AlterGeomFieldDefn(
     824           0 :         iGeomField, poNewGeomFieldDefn, nFlagsIn);
     825           0 :     if (eErr == OGRERR_NONE)
     826             :     {
     827             :         OGRGeomFieldDefn *poFieldDefn =
     828           0 :             m_poEditableFeatureDefn->GetGeomFieldDefn(iGeomField);
     829             :         OGRGeomFieldDefn *poMemFieldDefn =
     830           0 :             m_poMemLayer->GetLayerDefn()->GetGeomFieldDefn(iGeomField);
     831           0 :         poFieldDefn->SetName(poMemFieldDefn->GetNameRef());
     832           0 :         poFieldDefn->SetType(poMemFieldDefn->GetType());
     833           0 :         poFieldDefn->SetNullable(poMemFieldDefn->IsNullable());
     834           0 :         poFieldDefn->SetSpatialRef(poMemFieldDefn->GetSpatialRef());
     835           0 :         m_bStructureModified = true;
     836             :     }
     837           0 :     return eErr;
     838             : }
     839             : 
     840             : /************************************************************************/
     841             : /*                          CreateGeomField()                          */
     842             : /************************************************************************/
     843             : 
     844          16 : OGRErr OGREditableLayer::CreateGeomField(const OGRGeomFieldDefn *poField,
     845             :                                          int bApproxOK)
     846             : {
     847          16 :     if (!m_poDecoratedLayer || !m_bSupportsCreateGeomField)
     848           0 :         return OGRERR_FAILURE;
     849             : 
     850          31 :     if (!m_bStructureModified &&
     851          15 :         m_poDecoratedLayer->TestCapability(OLCCreateGeomField))
     852             :     {
     853          15 :         OGRErr eErr = m_poDecoratedLayer->CreateGeomField(poField, bApproxOK);
     854          15 :         if (eErr == OGRERR_NONE)
     855             :         {
     856          14 :             eErr = m_poMemLayer->CreateGeomField(poField, bApproxOK);
     857          14 :             if (eErr == OGRERR_NONE)
     858             :             {
     859          14 :                 m_poEditableFeatureDefn->AddGeomFieldDefn(poField);
     860             :             }
     861             :         }
     862          15 :         return eErr;
     863             :     }
     864             : 
     865           1 :     OGRErr eErr = m_poMemLayer->CreateGeomField(poField, bApproxOK);
     866           1 :     if (eErr == OGRERR_NONE)
     867             :     {
     868           1 :         m_poEditableFeatureDefn->AddGeomFieldDefn(poField);
     869           1 :         m_bStructureModified = true;
     870             :     }
     871           1 :     return eErr;
     872             : }
     873             : 
     874             : /************************************************************************/
     875             : /*                             SyncToDisk()                             */
     876             : /************************************************************************/
     877             : 
     878         569 : OGRErr OGREditableLayer::SyncToDisk()
     879             : {
     880         569 :     if (!m_poDecoratedLayer || m_poSynchronizer == nullptr)
     881           0 :         return OGRERR_FAILURE;
     882         569 :     OGRErr eErr = m_poDecoratedLayer->SyncToDisk();
     883         569 :     if (eErr == OGRERR_NONE)
     884             :     {
     885        1692 :         if (m_oSetCreated.empty() && m_oSetEdited.empty() &&
     886        1692 :             m_oSetDeleted.empty() && !m_bStructureModified)
     887             :         {
     888         556 :             return OGRERR_NONE;
     889             :         }
     890          13 :         eErr = m_poSynchronizer->EditableSyncToDisk(this, &m_poDecoratedLayer);
     891             :     }
     892          13 :     m_oSetCreated.clear();
     893          13 :     m_oSetEdited.clear();
     894          13 :     m_oSetDeleted.clear();
     895          13 :     m_oSetDeletedFields.clear();
     896          13 :     m_bStructureModified = false;
     897          13 :     return eErr;
     898             : }
     899             : 
     900             : /************************************************************************/
     901             : /*                          StartTransaction()                          */
     902             : /************************************************************************/
     903             : 
     904          36 : OGRErr OGREditableLayer::StartTransaction()
     905             : 
     906             : {
     907          36 :     return OGRLayer::StartTransaction();
     908             : }
     909             : 
     910             : /************************************************************************/
     911             : /*                         CommitTransaction()                          */
     912             : /************************************************************************/
     913             : 
     914          33 : OGRErr OGREditableLayer::CommitTransaction()
     915             : 
     916             : {
     917          33 :     return OGRLayer::CommitTransaction();
     918             : }
     919             : 
     920             : /************************************************************************/
     921             : /*                        RollbackTransaction()                         */
     922             : /************************************************************************/
     923             : 
     924           4 : OGRErr OGREditableLayer::RollbackTransaction()
     925             : 
     926             : {
     927           4 :     return OGRLayer::RollbackTransaction();
     928             : }
     929             : 
     930             : /************************************************************************/
     931             : /*                         GetGeometryColumn()                          */
     932             : /************************************************************************/
     933             : 
     934           9 : const char *OGREditableLayer::GetGeometryColumn()
     935             : 
     936             : {
     937           9 :     return OGRLayer::GetGeometryColumn();
     938             : }
     939             : 
     940             : //! @endcond

Generated by: LCOV version 1.14