paludis  Version 2.6.0
config_file.hh
Go to the documentation of this file.
1 /* vim: set sw=4 sts=4 et foldmethod=syntax : */
2 
3 /*
4  * Copyright (c) 2006, 2007, 2008, 2009, 2010, 2011 Ciaran McCreesh
5  *
6  * This file is part of the Paludis package manager. Paludis is free software;
7  * you can redistribute it and/or modify it under the terms of the GNU General
8  * Public License version 2, as published by the Free Software Foundation.
9  *
10  * Paludis is distributed in the hope that it will be useful, but WITHOUT ANY
11  * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12  * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
13  * details.
14  *
15  * You should have received a copy of the GNU General Public License along with
16  * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
17  * Place, Suite 330, Boston, MA 02111-1307 USA
18  */
19 
20 #ifndef PALUDIS_GUARD_PALUDIS_CONFIG_FILE_HH
21 #define PALUDIS_GUARD_PALUDIS_CONFIG_FILE_HH 1
22 
23 #include <paludis/util/config_file-fwd.hh>
24 #include <paludis/util/map-fwd.hh>
26 #include <paludis/util/pimp.hh>
28 #include <paludis/util/wrapped_forward_iterator.hh>
29 #include <paludis/util/fs_path-fwd.hh>
30 
31 #include <iosfwd>
32 #include <string>
33 #include <memory>
34 #include <functional>
35 
36 /** \file
37  * Declarations for the ConfigFile classes.
38  *
39  * \ingroup g_config_file
40  *
41  * \section Examples
42  *
43  * - None at this time.
44  */
45 
46 namespace paludis
47 {
48  /**
49  * Raised if an error is encountered parsing a configuration file.
50  *
51  * \ingroup g_config_file
52  * \ingroup g_exceptions
53  * \nosubgrouping
54  */
56  public ConfigurationError
57  {
58  public:
59  ///\name Basic operations
60  ///\{
61 
62  /**
63  * Constructor, where the filename is known.
64  *
65  * \param filename The filename in which the error occurred. May be a blank string, if
66  * the filename is not necessarily known.
67  * \param message A description of the error.
68  */
69  ConfigFileError(const std::string & filename, const std::string & message) noexcept;
70 
71  /**
72  * Constructor, where the filename is not known.
73  *
74  * \param message A description of the error.
75  */
76  ConfigFileError(const std::string & message) noexcept;
77 
78  ///\}
79  };
80 
81  /**
82  * Base class for configuration files.
83  *
84  * Data is read in from a ConfigFile::Source instance, which can be created from
85  * an FSPath, a std::istream or a string.
86  *
87  * \see KeyValueConfigFile
88  * \see LineConfigFile
89  *
90  * \ingroup g_config_file
91  * \nosubgrouping
92  */
94  {
95  public:
96  /**
97  * A source (for example, a file or a string) usable by ConfigFile.
98  *
99  * \see ConfigFile
100  * \ingroup g_config_file
101  * \nosubgrouping
102  */
104  {
105  private:
106  Pimp<Source> _imp;
107 
108  public:
109  ///\name Basic operations
110  ///\{
111 
112  Source(const FSPath &);
113  Source(const std::string &);
114  Source(std::istream &);
115 
116  Source(const Source &);
117  const Source & operator= (const Source &);
118 
119  ~Source();
120 
121  ///\}
122 
123  /**
124  * Our text, for use by ConfigFile.
125  */
126  const std::string & text() const PALUDIS_ATTRIBUTE((warn_unused_result));
127 
128  /**
129  * Our filename (may be empty), for use by ConfigFile.
130  */
131  const std::string & filename() const PALUDIS_ATTRIBUTE((warn_unused_result));
132  };
133 
134  ///\name Basic operations
135  ///\{
136 
137  virtual ~ConfigFile() = 0;
138 
139  ///\}
140  };
141 
142  /**
143  * A line-based configuration file.
144  *
145  * Various syntax options are available, and are controlled by LineConfigFileOptions:
146  *
147  * - Unless lcfo_disallow_continuations, lines ending in a backslash are continuations
148  * - Unless lcfo_disallow_comments, lines starting with a \# are comments
149  * - Unless lcfo_preserve_whitespace, leading and trailing whitespace is stripped
150  * - Unless lcfo_no_skip_blank_lines, blank lines are skipped.
151  *
152  * \ingroup g_config_file
153  * \nosubgrouping
154  */
156  public ConfigFile
157  {
158  private:
160 
161  public:
162  ///\name Basic operations
163  ///\{
164 
165  LineConfigFile(const Source &, const LineConfigFileOptions &);
166 
167  ~LineConfigFile();
168 
169  ///\}
170 
171  ///\name Iterate over our lines
172  ///\{
173 
174  struct ConstIteratorTag;
176 
177  ConstIterator begin() const PALUDIS_ATTRIBUTE((warn_unused_result));
178  ConstIterator end() const PALUDIS_ATTRIBUTE((warn_unused_result));
179 
180  ///\}
181  };
182 
183  /**
184  * A key=value configuration file.
185  *
186  * Various syntax options are available, and are controlled by KeyValueConfigFileOptions:
187  *
188  * - Unless kvcfo_disallow_continuations, line continuations via backslashes are allowed.
189  * - Unless kvcfo_disallow_comments, comments start with a \#.
190  * - Unless kvcfo_disallow_space_around_equals, the equals sign can have surrounding whitespace.
191  * - Unless kvcfo_disallow_space_inside_unquoted_values, foo = bar baz is legal.
192  * - Unless kvcfo_disallow_single_quoted_strings, single quoted strings are legal.
193  * - Unless kvcfo_disallow_double_quoted_strings, double quoted strings are legal.
194  * - Unless kvcfo_disallow_unquoted_values, unquoted values are legal.
195  * - Unless kvcfo_disallow_variables, variables using $foo and ${foo} are expanded.
196  * - Unless kvcfo_disallow_source, source path is legal.
197  * - Unless kvcfo_preserve_whitespace, leading and trailing whitespace on values is stripped.
198  * - If kvcfo_allow_sections, sections in the form "[foo]" and "[foo bar]" are allowed. A key
199  * 'baz' in section "[foo]" will be treated as "foo/baz", and "[foo bar]" as "foo/bar/baz".
200  *
201  * \ingroup g_config_file
202  * \nosubgrouping
203  */
205  public ConfigFile
206  {
207  private:
209 
210  public:
211  typedef std::function<std::string (const KeyValueConfigFile &, const std::string &)> DefaultFunction;
212  typedef std::function<std::string (const KeyValueConfigFile &,
213  const std::string & var, const std::string & old_value, const std::string & new_value)> TransformationFunction;
214 
215  static std::string no_defaults(const KeyValueConfigFile &, const std::string &);
216  static std::string no_transformation(const KeyValueConfigFile &, const std::string &, const std::string &, const std::string &);
217 
218  ///\name Basic operations
219  ///\{
220 
221  /**
222  * Constructor.
223  *
224  * \since 0.28
225  */
227  const Source &,
229  const DefaultFunction &,
230  const TransformationFunction &
231  );
232 
234 
235  ///\}
236 
237  ///\name Iterate over our keys
238  ///\{
239 
240  struct ConstIteratorTag;
241  typedef WrappedForwardIterator<ConstIteratorTag,
242  const std::pair<const std::string, std::string> > ConstIterator;
243  ConstIterator begin() const PALUDIS_ATTRIBUTE((warn_unused_result));
244  ConstIterator end() const PALUDIS_ATTRIBUTE((warn_unused_result));
245 
246  ///\}
247 
248  /**
249  * Fetch the value for a particular key.
250  */
251  std::string get(const std::string &) const PALUDIS_ATTRIBUTE((warn_unused_result));
252 
253  const KeyValueConfigFileOptions & options() const PALUDIS_ATTRIBUTE((warn_unused_result));
254  const DefaultFunction & default_function() const PALUDIS_ATTRIBUTE((warn_unused_result));
255  const TransformationFunction & transformation_function() const PALUDIS_ATTRIBUTE((warn_unused_result));
256  };
257 
258  extern template class Pimp<ConfigFile::Source>;
259  extern template class Pimp<LineConfigFile>;
260  extern template class Pimp<KeyValueConfigFile>;
261 
264 }
265 
266 #endif
Definition: pimp.hh:51
Definition: about_metadata-fwd.hh:23
Definition: config_file.hh:93
Definition: config_file.hh:204
Definition: config_file.hh:103
Definition: wrapped_forward_iterator-fwd.hh:26
Definition: options-fwd.hh:34
Definition: config_file.hh:55
Definition: config_file.hh:155
Definition: exception.hh:200
Definition: fs_path.hh:33
#define PALUDIS_ATTRIBUTE(x)
Definition: attributes.hh:53
#define PALUDIS_VISIBLE
Definition: attributes.hh:59