Menu

Diff of /src/glib/gmapfile.h [000000] .. [r1]  Maximize  Restore

Switch to side-by-side view

--- a
+++ b/src/glib/gmapfile.h
@@ -0,0 +1,154 @@
+//
+// Copyright (C) 2017 Graeme Walker
+// 
+// This program is free software: you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation, either version 3 of the License, or
+// (at your option) any later version.
+// 
+// This program is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+// 
+// You should have received a copy of the GNU General Public License
+// along with this program.  If not, see <http://www.gnu.org/licenses/>.
+// ===
+///
+/// \file gmapfile.h
+///
+
+#ifndef G_MAP_FILE_H
+#define G_MAP_FILE_H
+
+#include "gdef.h"
+#include "gpath.h"
+#include "gstrings.h"
+#include "goptionvalue.h"
+#include "goptionmap.h"
+#include <map>
+#include <string>
+#include <iostream>
+
+namespace G
+{
+	class MapFile ;
+}
+
+/// \class G::MapFile
+/// A class for reading and editing key=value files, supporting the creation of 
+/// backup files, variable expansion, character-set encoding and logging.
+/// \see G::OptionValue
+/// 
+class G::MapFile
+{
+public:
+	MapFile() ;
+		///< Constructor for an empty map.
+
+	explicit MapFile( const G::StringMap & map ) ;
+		///< Constructor that reads from a string map.
+
+	explicit MapFile( const OptionMap & map , const std::string & yes = std::string() ) ;
+		///< Constructor that reads from an option value map, typically parsed out
+		///< from a command-line. Unvalued 'true' options in the option value map 
+		///< are loaded into this mapfile object with a value given by the 'yes' 
+		///< parameter, whereas unvalued 'false' options are not loaded. Multi-valued
+		///< options are loaded as a comma-separated list.
+
+	explicit MapFile( const G::Path & , bool utf8 = false ) ;
+		///< Constructor that reads from a file.
+
+	explicit MapFile( std::istream & , bool utf8 = false ) ;
+		///< Constructor that reads from a stream.
+
+	const G::StringArray & keys() const ;
+		///< Returns a reference to the ordered list of keys.
+
+	static void check( const G::Path & , bool utf8 = false ) ;
+		///< Throws if the file is invalid. This is equivalent to constructing 
+		///< a temporary MapFile object, but it specifically does not do 
+		///< any logging.
+
+	void add( const std::string & key , const std::string & value ) ;
+		///< Adds or updates a single item in the map.
+
+	void writeItem( std::ostream & , const std::string & key , bool utf8 = false ) const ;
+		///< Writes a single item from this map to the stream.
+
+	static void writeItem( std::ostream & , const std::string & key , const std::string & value , bool utf8 = false ) ;
+		///< Writes an arbitrary item to the stream.
+
+	void editInto( const G::Path & path , bool make_backup = true ,
+		bool allow_read_error = false , bool allow_write_error = false , bool utf8 = false ) const ;
+			///< Edits an existing file so that its contents reflect this map.
+
+	bool contains( const std::string & key ) const ;
+		///< Returns true if the map contains the given key.
+
+	G::Path pathValue( const std::string & key ) const ;
+		///< Returns a mandatory path value from the map. Throws if it does not exist.
+
+	G::Path pathValue( const std::string & key , const G::Path & default_ ) const ;
+		///< Returns a path value from the map.
+
+	G::Path expandedPathValue( const std::string & key ) const ;
+		///< Returns a mandatory path value from the map with expand(). Throws if it does not exist.
+
+	G::Path expandedPathValue( const std::string & key , const G::Path & default_ ) const ;
+		///< Returns a path value from the map with expand().
+
+	unsigned int numericValue( const std::string & key , unsigned int default_ ) const ;
+		///< Returns a numeric value from the map.
+
+	std::string value( const std::string & key , const std::string & default_ = std::string() ) const ;
+		///< Returns a string value from the map.
+
+	std::string value( const std::string & key , const char * default_ ) const ;
+		///< Returns a string value from the map.
+
+	bool booleanValue( const std::string & key , bool default_ ) const ;
+		///< Returns a boolean value from the map.
+
+	void remove( const std::string & key ) ;
+		///< Removes a value (if it exists).
+
+	const G::StringMap & map() const ;
+		///< Returns a reference to the internal map.
+
+	void log() const ;
+		///< Logs the contents.
+
+	std::string expand( const std::string & value ) const ;
+		///< Does one-pass variable substitution for the given string.
+		///< Sub-strings like "%xyz%" are replaced by 'value("xyz")'
+		///< and "%%" is replaced by "%". If there are no appropriate
+		///< value in the map then the sub-string is left alone
+		///< (so "%xyz%" remains as "%xyz%" if there is no "xyz"
+		///< map item).
+
+private:
+	typedef std::list<std::string> List ;
+	void readFrom( const G::Path & , bool ) ;
+	void readFrom( std::istream & ss , bool ) ;
+	static std::string quote( const std::string & ) ;
+	List read( const G::Path & , bool ) const ;
+	void commentOut( List & ) const ;
+	void replace( List & , bool ) const ;
+	bool expand_( std::string & ) const ;
+	std::string expandAll( const std::string & ) const ;
+	static void backup( const G::Path & ) ;
+	static void save( const G::Path & , List & , bool ) ;
+	void log( const std::string & , const std::string & ) const ;
+	static void log( bool , const std::string & , const std::string & ) ;
+	static std::string fromUtf( const std::string & value , bool utf8 ) ;
+	static std::string toUtf( const std::string & value , bool utf8 ) ;
+	std::string mandatoryValue( const std::string & ) const ;
+
+private:
+	bool m_logging ;
+	G::StringMap m_map ;
+	G::StringArray m_keys ; // kept in input order
+} ;
+
+#endif