00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 #ifndef _MPCL_UTIL_PREFS_CONFIG_PROCESSOR__
00028 #define _MPCL_UTIL_PREFS_CONFIG_PROCESSOR__
00029 
00030 #include <set>
00031 #include <vector>
00032 #include "../../io/streamable.hh"
00033 #include "../../text/string.hh"
00034 #include "../collection/string_to_string_map.hh"
00035 #include "defs.hh"
00036 #include "option.hh"
00037 
00038 
00040 namespace mpcl
00041 {
00042   
00044   namespace util
00045   {
00046 
00048     namespace prefs
00049     {
00050 
00051       using io::IStreamable;
00052       using std::vector;
00053       using util::collection::TStringToStringMap;
00054 
00081       class TConfigProcessor : public IStreamable<>
00082       {
00083 
00084         public:
00085 
00086           typedef
00087             vector<TOption>::size_type
00088             size_type;
00089 
00091           typedef
00092             vector<TOption>
00093             TOptionVector;
00094 
00095 
00096         protected:
00097 
00099           static const unsigned int   _kuiMinPadding = 5;
00100 
00102           static const unsigned int   _kuiTerminalWidth = 80;
00103 
00105           bool   gInputConfigFile;
00106 
00108           mutable bool   gOptionsProcessed;
00109 
00114           int   iParametersCount;
00115 
00117           const char**   ppkcParametersList;
00118 
00129           mutable vector<TString>   tCommandLineArgumentsArray;
00130 
00132           TStringToStringMap   tEnvironmentVariableMap;
00133 
00154           mutable TOptionVector   tOptionVector;
00155 
00157           std::set<TString>   tValidNameSpaceSet;
00158 
00164           TString   yConfigFileName;
00165 
00170           TString   yCurrentNameSpace;
00171 
00173           TString   yUsageHeader;
00174 
00175 
00176         public:
00177 
00178           
00179           
00180           
00181 
00183           TConfigProcessor (void)                 :
00184             IStreamable<>              ()         ,
00185             gInputConfigFile           (false)    ,
00186             gOptionsProcessed          (false)    ,
00187             iParametersCount           (0)        ,
00188             ppkcParametersList         (NULL)     ,        
00189             tCommandLineArgumentsArray ()         ,
00190             tEnvironmentVariableMap    ()         ,
00191             tOptionVector              ()         ,
00192             tValidNameSpaceSet         ()         ,
00193             yConfigFileName            ()         ,
00194             yCurrentNameSpace          ()         ,
00195             yUsageHeader               ("Usage:")
00196           {
00197             addEnvironmentVariable ("HOME");
00198           }
00199 
00206           TConfigProcessor ( int          iPARAMETER_COUNT ,
00207                              const char** ppkcPARAMETERS   ) :
00208             IStreamable<>              ()                    ,
00209             gInputConfigFile           (false)               ,
00210             gOptionsProcessed          (false)               ,
00211             iParametersCount           (iPARAMETER_COUNT)    ,
00212             ppkcParametersList         (ppkcPARAMETERS)      ,
00213             tCommandLineArgumentsArray ()                    ,
00214             tEnvironmentVariableMap    ()                    ,
00215             tOptionVector              ()                    ,
00216             tValidNameSpaceSet         ()                    ,
00217             yConfigFileName            ()                    ,
00218             yCurrentNameSpace          ()                    ,
00219             yUsageHeader               ("Usage:")  
00220           {
00221             addEnvironmentVariable ("HOME");
00222             yConfigFileName = "conf." + programFileName();
00223           }
00224 
00226           virtual ~TConfigProcessor (void) {}
00227 
00235           virtual void addOption ( const TString& rkyNAME     ,
00236                                    const TString& rkySHORTCUT );
00237 
00246           virtual void addOption ( const TString& rkyNAME          ,
00247                                    const TString& rkySHORTCUT      ,
00248                                    const TString& rkyDEFAULT_VALUE );
00249 
00258           void addEnvironmentVariable ( const char* pkcENVIRONMENT_NAME ,
00259                                         bool        gREQUIRED = false   )
00260             throw (TVariableNotFoundException);
00261 
00263           virtual void processOptions (void)
00264           {
00265             if ( !gOptionsProcessed )
00266             {
00267               processConfigFile();
00268               processCommandLine();
00269               gOptionsProcessed = true;
00270             }
00271           }
00272 
00274           void setConfigFileName (const char* pkcCONFIG_FILE_NAME)
00275           {
00276             gOptionsProcessed = false;
00277             yConfigFileName   = pkcCONFIG_FILE_NAME;
00278             gInputConfigFile  = true;
00279           }
00280 
00286           void setCommandLineParameters ( int          iPARAMETER_COUNT ,
00287                                           const char** ppkcPARAMETERS   )
00288           {
00289             gOptionsProcessed  = false;
00290             iParametersCount   = iPARAMETER_COUNT;
00291             ppkcParametersList = ppkcPARAMETERS;
00292           }
00293 
00294           void setRootNameSpace (void)
00295           {
00296             yCurrentNameSpace.erase();
00297           }
00298 
00305           void setCurrentNameSpace (const TString& rkyNAME_SPACE)
00306           {
00307             yCurrentNameSpace = rkyNAME_SPACE;
00308             yCurrentNameSpace.lowercase();
00309             if ( tValidNameSpaceSet.find (yCurrentNameSpace) == tValidNameSpaceSet.end() )
00310             {
00311               tValidNameSpaceSet.insert (yCurrentNameSpace);
00312             }
00313           }
00314 
00316           void setUsageStringHeader (const TString& rkyUSAGE_HEADER)
00317           {
00318             yUsageHeader = rkyUSAGE_HEADER;
00319           }
00320 
00321 
00322         protected:
00323 
00324           
00325           
00326           
00327 
00329           virtual void processCommandLine (void);
00330 
00332           virtual void processConfigFile (void);
00333 
00338           void read (std::basic_istream<char_type, traits_type>& rtSOURCE_ISTREAM);
00339 
00346           virtual TOption& updateOptionWithName ( const TString& rkyNAME  ,
00347                                                   const TString& rkyVALUE );
00348 
00355           virtual TOption& updateOptionWithShortcut ( const TString& rkySHORTCUT ,
00356                                                       const TString& rkyVALUE    );
00357 
00358 
00359         public:
00360 
00361           
00362           
00363           
00364 
00371           TString argumentValue (size_type zARGUMENT_INDEX) const
00372           {
00373             return tCommandLineArgumentsArray [zARGUMENT_INDEX];
00374           }
00375 
00380           TString environmentValue (const char* pkcENVIRONMENT_NAME) const
00381           {
00382             return tEnvironmentVariableMap [pkcENVIRONMENT_NAME];
00383           }
00384 
00390           bool hasArguments (void) const
00391           {
00392             return ( numberOfArguments() > 0 );
00393           }
00394 
00396           size_type numberOfArguments (void) const
00397           {
00398             return tCommandLineArgumentsArray.size();
00399           }
00400 
00406           TOption& operator [] (const char* pkcNAME)
00407             throw (TVariableNotFoundException);
00408 
00414           const TOption& operator [] (const char* pkcNAME) const
00415             throw (TVariableNotFoundException);
00416 
00417           const TOption& optionWithName (const TString& rkyNAME) const
00418           {
00419             return operator [] (rkyNAME.c_str());
00420           }
00421 
00423           TOption& optionWithName (const TString& rkyNAME)
00424           {
00425             return operator [] (rkyNAME.c_str());
00426           }
00427 
00429           TString formatUsageString (void) const;
00430 
00432           const TString programFileName (void) const;
00433 
00435           void saveConfigFile (void) const
00436             throw (TFileErrorException);
00437 
00438 
00439         protected:
00440 
00441           
00442           
00443           
00444 
00450           bool isThereOptionWithName (const char* pkcNAME) const;
00451 
00457           bool isThereOptionWithShortcut (const char* pkcSHORTCUT) const;
00458 
00460           unsigned int longestOptionLength (void) const;
00461 
00469           TString nameSpace (const TString& rkyNAME) const;
00470 
00472           TString nameForShortcut (const TString& rkySHORTCUT) const;
00473 
00475           TString shortcutForName (const TString& rkyNAME) const;
00476 
00482           void write (std::basic_ostream<char_type, traits_type>& rtTARGET_OSTREAM) const;
00483 
00484       };  
00485 
00486     }  
00487 
00488   }  
00489 
00490 }  
00491 
00492 
00493 #endif  // not _MPCL_UTIL_PREFS_CONFIG_PROCESSOR__