LCOV - code coverage report
Current view: top level - apps - gdalpipelinestepalgorithm.h (source / functions) Hit Total Coverage
Test: gdal_filtered.info Lines: 105 107 98.1 %
Date: 2026-06-23 16:35:19 Functions: 40 41 97.6 %

          Line data    Source code
       1             : /******************************************************************************
       2             :  *
       3             :  * Project:  GDAL
       4             :  * Purpose:  gdal "raster/vector pipeline" subcommand
       5             :  * Author:   Even Rouault <even dot rouault at spatialys.com>
       6             :  *
       7             :  ******************************************************************************
       8             :  * Copyright (c) 2024, Even Rouault <even dot rouault at spatialys.com>
       9             :  *
      10             :  * SPDX-License-Identifier: MIT
      11             :  ****************************************************************************/
      12             : 
      13             : #ifndef GDALPIPELINESTEPALGORITHM_INCLUDED
      14             : #define GDALPIPELINESTEPALGORITHM_INCLUDED
      15             : 
      16             : //! @cond Doxygen_Suppress
      17             : 
      18             : #include "gdalalgorithm.h"
      19             : 
      20             : #include "gdalpipelinestepruncontext.h"
      21             : 
      22             : /************************************************************************/
      23             : /*                      GDALPipelineStepAlgorithm                       */
      24             : /************************************************************************/
      25             : 
      26             : class OGRLayer;
      27             : 
      28             : class GDALPipelineStepAlgorithm /* non final */ : public GDALAlgorithm
      29             : {
      30             :   public:
      31         179 :     std::vector<GDALArgDatasetValue> &GetInputDatasets()
      32             :     {
      33         179 :         return m_inputDataset;
      34             :     }
      35             : 
      36             :     const std::vector<GDALArgDatasetValue> &GetInputDatasets() const
      37             :     {
      38             :         return m_inputDataset;
      39             :     }
      40             : 
      41         206 :     GDALArgDatasetValue &GetOutputDataset()
      42             :     {
      43         206 :         return m_outputDataset;
      44             :     }
      45             : 
      46             :     const GDALArgDatasetValue &GetOutputDataset() const
      47             :     {
      48             :         return m_outputDataset;
      49             :     }
      50             : 
      51         737 :     const std::string &GetOutputString() const
      52             :     {
      53         737 :         return m_output;
      54             :     }
      55             : 
      56          60 :     const std::string &GetOutputLayerName() const
      57             :     {
      58          60 :         return m_outputLayerName;
      59             :     }
      60             : 
      61         222 :     const std::string &GetOutputFormat() const
      62             :     {
      63         222 :         return m_format;
      64             :     }
      65             : 
      66         100 :     const std::vector<std::string> &GetCreationOptions() const
      67             :     {
      68         100 :         return m_creationOptions;
      69             :     }
      70             : 
      71          79 :     const std::vector<std::string> &GetLayerCreationOptions() const
      72             :     {
      73          79 :         return m_layerCreationOptions;
      74             :     }
      75             : 
      76          93 :     bool GetOverwriteLayer() const
      77             :     {
      78          93 :         return m_overwriteLayer;
      79             :     }
      80             : 
      81          52 :     bool GetAppendLayer() const
      82             :     {
      83          52 :         return m_appendLayer;
      84             :     }
      85             : 
      86             :     virtual int GetInputType() const = 0;
      87             : 
      88             :     virtual int GetOutputType() const = 0;
      89             : 
      90             :     bool Finalize() override;
      91             : 
      92             :     // Used by GDALDispatcherAlgorithm for vector info/convert
      93          41 :     GDALDataset *GetInputDatasetRef()
      94             :     {
      95          41 :         return m_inputDataset.empty() ? nullptr
      96          41 :                                       : m_inputDataset[0].GetDatasetRef();
      97             :     }
      98             : 
      99             :     // Used by GDALDispatcherAlgorithm for vector info/convert
     100             :     void SetInputDataset(GDALDataset *poDS);
     101             : 
     102             :   protected:
     103             :     struct ConstructorOptions
     104             :     {
     105             :         bool standaloneStep = false;
     106             :         bool addDefaultArguments = true;
     107             :         bool autoOpenInputDatasets = true;
     108             :         bool inputDatasetRequired = true;
     109             :         bool inputDatasetPositional = true;
     110             :         bool outputDatasetRequired = true;
     111             :         bool addInputLayerNameArgument = true;        // only for vector input
     112             :         bool addUpdateArgument = true;                // only for vector output
     113             :         bool addAppendLayerArgument = true;           // only for vector output
     114             :         bool addNoCreateEmptyLayersArgument = false;  // only for vector output
     115             :         bool addOverwriteLayerArgument = true;        // only for vector output
     116             :         bool addUpsertArgument = true;                // only for vector output
     117             :         bool addSkipErrorsArgument = true;            // only for vector output
     118             :         bool addOutputLayerNameArgument = true;       // only for vector output
     119             :         bool outputLayerNameAvailableInPipelineStep = false;
     120             :         int inputDatasetMaxCount = 1;
     121             :         int inputDatasetInputFlags = GADV_NAME | GADV_OBJECT;
     122             :         std::string inputDatasetHelpMsg{};
     123             :         std::string inputDatasetAlias{};
     124             :         std::string inputDatasetMetaVar = "INPUT";
     125             :         std::string outputDatasetHelpMsg{};
     126             :         std::string outputFormatCreateCapability = GDAL_DCAP_CREATECOPY;
     127             : 
     128       11992 :         inline ConstructorOptions &SetStandaloneStep(bool b)
     129             :         {
     130       11992 :             standaloneStep = b;
     131       11992 :             return *this;
     132             :         }
     133             : 
     134        6045 :         inline ConstructorOptions &SetAddDefaultArguments(bool b)
     135             :         {
     136        6045 :             addDefaultArguments = b;
     137        6045 :             return *this;
     138             :         }
     139             : 
     140         541 :         inline ConstructorOptions &SetAddInputLayerNameArgument(bool b)
     141             :         {
     142         541 :             addInputLayerNameArgument = b;
     143         541 :             return *this;
     144             :         }
     145             : 
     146         523 :         inline ConstructorOptions &SetInputDatasetRequired(bool b)
     147             :         {
     148         523 :             inputDatasetRequired = b;
     149         523 :             return *this;
     150             :         }
     151             : 
     152         523 :         inline ConstructorOptions &SetInputDatasetPositional(bool b)
     153             :         {
     154         523 :             inputDatasetPositional = b;
     155         523 :             return *this;
     156             :         }
     157             : 
     158        3386 :         inline ConstructorOptions &SetInputDatasetMaxCount(int maxCount)
     159             :         {
     160        3386 :             inputDatasetMaxCount = maxCount;
     161        3386 :             return *this;
     162             :         }
     163             : 
     164         256 :         inline ConstructorOptions &SetInputDatasetInputFlags(int flags)
     165             :         {
     166         256 :             inputDatasetInputFlags = flags;
     167         256 :             return *this;
     168             :         }
     169             : 
     170         654 :         inline ConstructorOptions &SetInputDatasetHelpMsg(const std::string &s)
     171             :         {
     172         654 :             inputDatasetHelpMsg = s;
     173         654 :             return *this;
     174             :         }
     175             : 
     176        1365 :         inline ConstructorOptions &SetInputDatasetAlias(const std::string &s)
     177             :         {
     178        1365 :             inputDatasetAlias = s;
     179        1365 :             return *this;
     180             :         }
     181             : 
     182        1058 :         inline ConstructorOptions &SetInputDatasetMetaVar(const std::string &s)
     183             :         {
     184        1058 :             inputDatasetMetaVar = s;
     185        1058 :             return *this;
     186             :         }
     187             : 
     188         272 :         inline ConstructorOptions &SetOutputDatasetHelpMsg(const std::string &s)
     189             :         {
     190         272 :             outputDatasetHelpMsg = s;
     191         272 :             return *this;
     192             :         }
     193             : 
     194        1628 :         inline ConstructorOptions &SetAutoOpenInputDatasets(bool b)
     195             :         {
     196        1628 :             autoOpenInputDatasets = b;
     197        1628 :             return *this;
     198             :         }
     199             : 
     200          98 :         inline ConstructorOptions &SetOutputDatasetRequired(bool b)
     201             :         {
     202          98 :             outputDatasetRequired = b;
     203          98 :             return *this;
     204             :         }
     205             : 
     206             :         inline ConstructorOptions &
     207        1904 :         SetOutputFormatCreateCapability(const std::string &capability)
     208             :         {
     209        1904 :             outputFormatCreateCapability = capability;
     210        1904 :             return *this;
     211             :         }
     212             : 
     213         334 :         inline ConstructorOptions &SetAddAppendLayerArgument(bool b)
     214             :         {
     215         334 :             addAppendLayerArgument = b;
     216         334 :             return *this;
     217             :         }
     218             : 
     219         203 :         inline ConstructorOptions &SetAddOverwriteLayerArgument(bool b)
     220             :         {
     221         203 :             addOverwriteLayerArgument = b;
     222         203 :             return *this;
     223             :         }
     224             : 
     225         203 :         inline ConstructorOptions &SetAddUpdateArgument(bool b)
     226             :         {
     227         203 :             addUpdateArgument = b;
     228         203 :             return *this;
     229             :         }
     230             : 
     231         627 :         inline ConstructorOptions &SetAddUpsertArgument(bool b)
     232             :         {
     233         627 :             addUpsertArgument = b;
     234         627 :             return *this;
     235             :         }
     236             : 
     237        1205 :         inline ConstructorOptions &SetNoCreateEmptyLayersArgument(bool b)
     238             :         {
     239        1205 :             addNoCreateEmptyLayersArgument = b;
     240        1205 :             return *this;
     241             :         }
     242             : 
     243         627 :         inline ConstructorOptions &SetAddSkipErrorsArgument(bool b)
     244             :         {
     245         627 :             addSkipErrorsArgument = b;
     246         627 :             return *this;
     247             :         }
     248             : 
     249         206 :         inline ConstructorOptions &SetAddOutputLayerNameArgument(bool b)
     250             :         {
     251         206 :             addOutputLayerNameArgument = b;
     252         206 :             return *this;
     253             :         }
     254             : 
     255             :         inline ConstructorOptions &
     256         599 :         SetOutputLayerNameAvailableInPipelineStep(bool b)
     257             :         {
     258         599 :             outputLayerNameAvailableInPipelineStep = b;
     259         599 :             return *this;
     260             :         }
     261             :     };
     262             : 
     263             :     GDALPipelineStepAlgorithm(const std::string &name,
     264             :                               const std::string &description,
     265             :                               const std::string &helpURL,
     266             :                               const ConstructorOptions &);
     267             : 
     268             :     friend class GDALPipelineAlgorithm;
     269             :     friend class GDALRasterPipelineAlgorithm;
     270             :     friend class GDALVectorPipelineAlgorithm;
     271             :     friend class GDALMdimPipelineAlgorithm;
     272             :     friend class GDALAbstractPipelineAlgorithm;
     273             : 
     274        2145 :     virtual bool CanBeFirstStep() const
     275             :     {
     276        2145 :         return false;
     277             :     }
     278             : 
     279         544 :     virtual bool CanBeMiddleStep() const
     280             :     {
     281         544 :         return !CanBeFirstStep() && !CanBeLastStep();
     282             :     }
     283             : 
     284         921 :     virtual bool CanBeLastStep() const
     285             :     {
     286         921 :         return false;
     287             :     }
     288             : 
     289             :     //! Whether a user parameter can cause a file to be written at a specified location
     290          54 :     virtual bool GeneratesFilesFromUserInput() const
     291             :     {
     292          54 :         return false;
     293             :     }
     294             : 
     295         830 :     virtual bool IsNativelyStreamingCompatible() const
     296             :     {
     297         830 :         return true;
     298             :     }
     299             : 
     300         281 :     virtual bool SupportsInputMultiThreading() const
     301             :     {
     302         281 :         return false;
     303             :     }
     304             : 
     305        1502 :     virtual bool CanHandleNextStep(GDALPipelineStepAlgorithm *) const
     306             :     {
     307        1502 :         return false;
     308             :     }
     309             : 
     310           0 :     virtual bool OutputDatasetAllowedBeforeRunningStep() const
     311             :     {
     312           0 :         return false;
     313             :     }
     314             : 
     315         276 :     virtual CPLJSONObject Get_OGR_SCHEMA_OpenOption_Layer() const
     316             :     {
     317         276 :         CPLJSONObject obj;
     318         276 :         obj.Deinit();
     319         276 :         return obj;
     320             :     }
     321             : 
     322             :     virtual bool RunStep(GDALPipelineStepRunContext &ctxt) = 0;
     323             : 
     324             :     bool m_standaloneStep = false;
     325             :     const ConstructorOptions m_constructorOptions;
     326             :     bool m_outputVRTCompatible = true;
     327             :     std::string m_helpDocCategory{};
     328             : 
     329             :     // Input arguments
     330             :     std::vector<GDALArgDatasetValue> m_inputDataset{};
     331             :     std::vector<std::string> m_openOptions{};
     332             :     std::vector<std::string> m_inputFormats{};
     333             :     std::vector<std::string> m_inputLayerNames{};
     334             : 
     335             :     // Output arguments
     336             :     bool m_stdout = false;
     337             :     std::string m_output{};
     338             :     GDALArgDatasetValue m_outputDataset{};
     339             :     std::string m_format{};
     340             :     std::vector<std::string> m_outputOpenOptions{};
     341             :     std::vector<std::string> m_creationOptions{};
     342             :     bool m_overwrite = false;
     343             :     std::string m_outputLayerName{};
     344             :     GDALInConstructionAlgorithmArg *m_outputFormatArg = nullptr;
     345             :     bool m_appendRaster = false;
     346             : 
     347             :     // Output arguments (vector specific)
     348             :     std::vector<std::string> m_layerCreationOptions{};
     349             :     bool m_update = false;
     350             :     bool m_overwriteLayer = false;
     351             :     bool m_appendLayer = false;
     352             :     bool m_upsert = false;
     353             :     bool m_skipErrors = false;
     354             :     bool m_noCreateEmptyLayers = false;
     355             : 
     356             :     void AddRasterInputArgs(bool openForMixedRasterVector, bool hiddenForCLI);
     357             :     void AddRasterOutputArgs(bool hiddenForCLI);
     358             :     void AddRasterHiddenInputDatasetArg();
     359             : 
     360             :     void AddVectorInputArgs(bool hiddenForCLI);
     361             :     void AddVectorHiddenInputDatasetArg();
     362             :     void AddVectorOutputArgs(bool hiddenForCLI,
     363             :                              bool shortNameOutputLayerAllowed);
     364             :     using GDALAlgorithm::AddOutputLayerNameArg;
     365             :     void AddOutputLayerNameArg(bool hiddenForCLI,
     366             :                                bool shortNameOutputLayerAllowed);
     367             : 
     368             :     void AddMdimInputArgs(bool openForMixedRasterVector, bool hiddenForCLI,
     369             :                           bool acceptRaster);
     370             :     void AddMdimOutputArgs(bool hiddenForCLI);
     371             :     void AddMdimHiddenInputDatasetArg();
     372             : 
     373             :     bool CreateDatasetSingleOutputLayerIfNeeded(
     374             :         GDALPipelineStepRunContext &ctxt, const std::string &defaultLayerName,
     375             :         GDALDataset *&poDstDS, bool &bTemporaryFile,
     376             :         std::unique_ptr<GDALDataset> &poNewRetDS, std::string &outputLayerName,
     377             :         OGRLayer *&poDstLayer);
     378             : 
     379             :   private:
     380             :     bool RunImpl(GDALProgressFunc pfnProgress, void *pProgressData) override;
     381             :     GDALAlgorithm::ProcessGDALGOutputRet ProcessGDALGOutput() override;
     382             :     bool CheckSafeForStreamOutput() override;
     383             : 
     384             :     CPL_DISALLOW_COPY_ASSIGN(GDALPipelineStepAlgorithm)
     385             : };
     386             : 
     387             : //! @endcond
     388             : 
     389             : #endif

Generated by: LCOV version 1.14