ApplicationSettings.h
Go to the documentation of this file.
1 /* Copyright (C) 2008 National Institute For Space Research (INPE) - Brazil.
2 
3  This file is part of the TerraLib - a Framework for building GIS enabled applications.
4 
5  TerraLib is free software: you can redistribute it and/or modify
6  it under the terms of the GNU Lesser General Public License as published by
7  the Free Software Foundation, either version 3 of the License,
8  or (at your option) any later version.
9 
10  TerraLib is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU Lesser General Public License for more details.
14 
15  You should have received a copy of the GNU Lesser General Public License
16  along with TerraLib. See COPYING. If not, write to
17  TerraLib Team at <terralib-team@terralib.org>.
18  */
19 
20 /*!
21  \file terralib/common/ApplicationSettings.h
22 
23  \brief A class for managing application settings.
24 */
25 
26 #ifndef __TERRALIB_COMMON_INTERNAL_APPLICATIONSETTINGS_H
27 #define __TERRALIB_COMMON_INTERNAL_APPLICATIONSETTINGS_H
28 
29 // TerraLib
30 #include "Config.h"
31 #include "ThreadingPolicies.h"
32 #include "../core/filesystem/FileSystem.h"
33 
34 // STL
35 #include <string>
36 
37 // Boost
38 #include <boost/property_tree/ptree.hpp>
39 #include <boost/property_tree/xml_parser.hpp>
40 #include <boost/filesystem.hpp>
41 #include <boost/noncopyable.hpp>
42 
43 namespace te
44 {
45  namespace common
46  {
47  /*!
48  \class ApplicationSettings
49 
50  \brief A class for managing application settings.
51 
52  This class can be used to keep user preferences that
53  customize the application's appearance and behavior.
54  It can also be used to keep settings applied to
55  the system (for all users).
56 
57  For each setting you must provide an unique name.
58  The rule for setting names are the same as
59  for XML element names: it can be any combination of letters,
60  numbers, or an underscore, they must not start with a number
61  and cannot have white spaces.
62 
63  \ingroup common
64 
65  \todo Make some methods that accept arrays (get and set)!!!
66  */
68  : public ObjectLevelLockable<ApplicationSettings,
69  ::boost::recursive_mutex,
70  ::boost::lock_guard< ::boost::recursive_mutex>,
71  ::boost::lock_guard< ::boost::recursive_mutex> >,
72  public ::boost::noncopyable
73  {
74  public:
75 
76  /*! \brief Constructor. */
78 
79  /*! \brief The destructor will automatically save the settings to a file if one is set. */
81 
82  /*!
83  \brief It stores the value according to the key.
84 
85  \param key The key used to identify the given value.
86  The key must follow the same rules as XML elements and they can be
87  subclassified using a dot notation: setValue(key.subkey.subsubkey, value).
88  \param value The value to be stored, any valid string.
89 
90  \note If you want to store a binary value you can encode it as an hex-string.
91 
92  \note Thread-safe depending on ThreadingPolicy.
93  */
94  void setValue(const std::string& key, const std::string& value);
95 
96  /*!
97  \brief It returns the value for a given key or empty.
98 
99  \param key The key used to identify the searched value.
100 
101  \return The value for a given key or empty.
102 
103  \note Thread-safe depending on ThreadingPolicy.
104  */
105  std::string getValue(const std::string& key);
106 
107  /*!
108  \brief It initializes the application settings.
109 
110  \param settingsFile The name of the application settings file.
111 
112  \note It discards all the settings and doesnt't save changes.
113 
114  \note If the informed file doesn't exist application settings will be empty after the excution of this method.
115 
116  \note Thread-safe depending on ThreadingPolicy.
117 
118  \todo Este metodo deveria aceitar uma URL!!!!!!
119  */
120  void load(const std::string& settingsFile);
121 
122  /*!
123  \brief It updates the application settings.
124 
125  \note This function is called automatically from ApplicationSettings's destructor.
126 
127  \note If application settings is empty it discards the config file.
128 
129  \note Thread-safe depending on ThreadingPolicy.
130  */
131  void update();
132 
133  /*!
134  \brief This method can be used by clients to inform manually
135  that the internal state has changed.
136 
137  This method is useful when accessing the internal settings structure.
138 
139  \note Thread-safe depending on ThreadingPolicy.
140  */
141  void changed();
142 
143  /*!
144  \brief It return a reading reference to the internal settings.
145 
146  \return A read reference to the internal settings.
147 
148  \note Take care when keeping a reference to this property in a multi-thread environment.
149  */
150  const boost::property_tree::ptree& getAllSettings() const;
151 
152  /*!
153  \brief It return a reference to the internal settings.
154 
155  \return A reference to the internal settings.
156 
157  \note Depending on the ThreadingPolicy you can synchronize the read/write from/to the settings.
158  The client of this method will be responsible for informing changes. Release any lock before calling
159  the update method or any other thread-safe method if you are not using a recursive mutex in the
160  threading policy.
161  */
162  boost::property_tree::ptree& getAllSettings();
163 
164  protected:
165 
166  boost::property_tree::ptree m_settings; //!< This will keep our settings in memory.
167  std::string m_file; //!< The settings file name.
168  bool m_dirty; //!< A dirty bit to indicate wheter the clients have made changes in the settings since the last update.
169  };
170 
172  : m_dirty(false)
173  {
174  }
175 
176  inline
178  {
179  update();
180  }
181 
182  inline void ApplicationSettings::setValue(const std::string& key, const std::string& value)
183  {
184  LockWrite l(this);
185 
186  m_settings.put(key, value);
187  m_dirty = true;
188  }
189 
190  inline std::string ApplicationSettings::getValue(const std::string& key)
191  {
192  LockRead l(this);
193 
194  try
195  {
196  return m_settings.get<std::string>(key);
197  }
198  catch(...)
199  {
200  return "";
201  }
202  }
203 
204  inline void ApplicationSettings::load(const std::string& settingsFile)
205  {
206  LockWrite l(this);
207 
208  m_dirty = false;
209  m_settings.clear();
210  m_file = settingsFile;
211 
213  boost::property_tree::read_xml(m_file, m_settings, boost::property_tree::xml_parser::trim_whitespace);
214  }
215 
217  {
218  LockWrite l(this);
219 
220  if(m_dirty == false)
221  return;
222 
223  if(m_settings.empty())
225  else
226  {
227 #if BOOST_VERSION > 105600
228  boost::property_tree::xml_writer_settings<std::string> settings('\t', 1);
229 #else
230  boost::property_tree::xml_writer_settings<char> settings('\t', 1);
231 #endif
232  boost::property_tree::write_xml(m_file, m_settings, std::locale(), settings);
233  }
234 
235  m_dirty = false;
236  }
237 
239  {
240  LockWrite l(this);
241 
242  m_dirty = true;
243  }
244 
245  inline const boost::property_tree::ptree& ApplicationSettings::getAllSettings() const
246  {
247  return m_settings;
248  }
249 
250  inline boost::property_tree::ptree& ApplicationSettings::getAllSettings()
251  {
252  return m_settings;
253  }
254 
255  } // end namespace common
256 } // end namespace te
257 
258 #endif // __TERRALIB_COMMON_INTERNAL_APPLICATIONSETTINGS_H
259 
bool m_dirty
A dirty bit to indicate wheter the clients have made changes in the settings since the last update...
void load(const std::string &settingsFile)
It initializes the application settings.
static bool isRegularFile(const std::string &path)
Checks if a given path in UTF-8 is a regular file.
Configuration flags for the TerraLib Common Runtime module.
void changed()
This method can be used by clients to inform manually that the internal state has changed...
void setValue(const std::string &key, const std::string &value)
It stores the value according to the key.
std::string m_file
The settings file name.
URI C++ Library.
Threading policies that can be applied to TerraLib classes that need some synchronization schema...
~ApplicationSettings()
The destructor will automatically save the settings to a file if one is set.
const boost::property_tree::ptree & getAllSettings() const
It return a reading reference to the internal settings.
std::string getValue(const std::string &key)
It returns the value for a given key or empty.
This policy assures an object-level locking scheme for a derived class.
static bool remove(const std::string &path)
Removes a file or directory from a given path in UTF-8.
boost::property_tree::ptree m_settings
This will keep our settings in memory.
void update()
It updates the application settings.
A class for managing application settings.