/**
* @file		configuration.h
* @brief	Interfaces for loading/storing configuration values.
* @author	Cesar Mauri Loba (cesar at crea-si dot com)
*
* -------------------------------------------------------------------------
*
* Copyright:   (C) 2010 Cesar Mauri Loba - CREA Software Systems
*
*  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/>.
*/
#ifndef SPCORE_CONFIGURATION_H
#define SPCORE_CONFIGURATION_H

#include "spcore/baseobj.h"
#include <stdio.h>

namespace spcore {

/**
	@brief Interface class for configuration objects.

	Paths may consist only of alphanumeric characters, dashes (‘-’) and 
	underscores (‘_’). Slash character "/" is used to separate levels. 
	If the first character is '/' denotes an absolute path, otherwise 
	it is a relative to the current path. The current path can be changed 
	using the SetPath() method.
*/
class IConfiguration : public IBaseObject {
protected:
	virtual ~IConfiguration() {}

public:

	/**
		@brief Load configuration from file.
		@param instream opened input file stream.
		@return true when loaded successfully, false when error.
	*/
	virtual bool Load (FILE* instream)= 0;

	/**
		@brief Save current configuration to file.
		@param outstream opened output file stream.
		@return true when saved successfully, false when error.
	*/
	virtual bool Save (FILE* outstream) const= 0;
   
	/**
		@brief Read a string.
		@param path path that uniquely identifies the key.
		@param str read string (storage is managed internally, so
			the pointer SHOULD NOT be freed).
		@return true if the value was read.
	*/
	virtual bool ReadString (const char* path, const char** str) const= 0;
	
	/**
		@brief Read an integer.
		@param path path that uniquely identifies the key.
		@param i pointer to where the read value will be stored.
		@return true if the value was read.
	*/
	virtual bool ReadInt (const char* path, int* i) const= 0;
	
	/**
		@brief Read a 64bit integer.
		@param path path that uniquely identifies the key.
		@param i pointer to where the read value will be stored.
		@return true if the value was read.
	*/
	virtual bool ReadInt64 (const char* path, long long* i) const= 0;
	
	/**
		@brief Read a double.
		@param path path that uniquely identifies the key.
		@param d pointer to where the read value will be stored.
		@return true if the value was read.
	*/
	virtual bool ReadDouble (const char* path, double* d) const= 0;
	
	/**
		@brief Read a boolean.
		@param path path that uniquely identifies the key.
		@param b pointer to where the read value will be stored.
		@return true if the value was read.
	*/
	virtual bool ReadBool (const char* path, bool* b) const= 0;
	
	
	/**
		@brief Write a string.
		@param path path that uniquely identifies the key.
		@param str string to write.
		@return true if the value was written.
	*/
	virtual bool WriteString (const char* path, const char* str)= 0;
	
	/**
		@brief Write an integer.
		@param path path that uniquely identifies the key.
		@param i integer to write.
		@return true if the value was written.
	*/
	virtual bool WriteInt (const char* path, int i)= 0;
	
	/**
		@brief Write a 64bit integer.
		@param path path that uniquely identifies the key.
		@param i 64bit integer to write.
		@return true if the value was written.
	*/
	virtual bool WriteInt64 (const char* path, long long i)= 0;
	
	/**
		@brief Write a double.
		@param path path that uniquely identifies the key.
		@param d floating point value to write.
		@return true if the value was written.
	*/
	virtual bool WriteDouble (const char* path, double d)= 0;
	
	/**
		@brief Write a boolean.
		@param path path that uniquely identifies the key.
		@param b value to write.
		@return true if the value was written.
	*/
	virtual bool WriteBool (const char* path, bool b)= 0;
	
	/**
		@brief Removes an element given its path.
		@param path path that uniquely identifies the key.
		@return true if the value was removed.
	*/
	virtual bool Remove (const char* path)= 0;

	/**
		@brief Set current path.
		@param path New path to change to. '..' is supported. If path does not exists it is created.
		@return true if the path was successfully set. 
	*/
	virtual bool SetPath (const char* path)= 0;
};

} // namespace spcore
#endif
