source: nscp/include/settings/client/settings_client.hpp @ 83c2453

0.4.00.4.10.4.2
Last change on this file since 83c2453 was 83c2453, checked in by Michael Medin <michael@…>, 15 months ago
  • Fixed performance data parsing issue
  • Fixed external scripts performance data issue
  • Fixed boolean flag handling in settings (default generated as false regardless of actual state)
  • Fixed so "advanced properties" are not generated with --update-defaults
  • Added some "advanced properties" here and there
  • Fixed path handling for object
  • Added last few features to the GraphitePlugin? (which is now usable)
  • Tweaked nscp settings command line syntax a bit to be more flexible and usable...
  • Property mode set to 100644
File size: 26.1 KB
Line 
1#pragma once
2
3#include <map>
4#include <list>
5#include <string>
6
7#include <boost/any.hpp>
8#include <boost/bind.hpp>
9#include <boost/function.hpp>
10#include <boost/shared_ptr.hpp>
11#include <boost/foreach.hpp>
12
13#include <unicode_char.hpp>
14#include <strEx.h>
15
16#include <nscapi/nscapi_core_wrapper.hpp>
17#include <settings/client/settings_client_interface.hpp>
18
19namespace nscapi {
20        namespace settings_helper {
21
22                typedef boost::shared_ptr<settings_impl_interface> settings_impl_interface_ptr;
23
24                class key_interface {
25                public:
26                        virtual NSCAPI::settings_type get_type() const = 0;
27                        virtual std::wstring get_default_as_string() const = 0;
28                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path, std::wstring key) const = 0;
29                        virtual void notify(settings_impl_interface_ptr core_, std::wstring parent, std::wstring path, std::wstring key) const = 0;
30                };
31                template<class T>
32                class typed_key : public key_interface {
33                public:
34                        typed_key(const T& v, bool has_default)  : has_default_(has_default), default_value_(boost::any(v)), default_value_as_text_(boost::lexical_cast<std::wstring>(v)) {}
35                        typed_key(bool has_default)  : has_default_(has_default) {}
36
37                        virtual typed_key* default_value(const T& v) {
38                                default_value_ = boost::any(v);
39                                default_value_as_text_ = boost::lexical_cast<std::wstring>(v);
40                                return this;
41                        }
42
43                        virtual std::wstring get_default_as_string() const {
44                                return default_value_as_text_;
45                        }
46                        virtual void update_target(T *value) const = 0;
47                protected:
48                        bool has_default_;
49                        boost::any default_value_;
50                        std::wstring default_value_as_text_;
51                };
52
53                template<class T>
54                class typed_string_value : public typed_key<T> {
55                public:
56                        typed_string_value(const T& v, bool has_default) : typed_key<T>(v, has_default) {}
57                        //typed_string_value() : typed_key<T>() {}
58                        virtual NSCAPI::settings_type get_type() const {
59                                return NSCAPI::key_string;
60                        }
61                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path, std::wstring key) const {
62                                std::wstring dummy(_T("$$DUMMY_VALUE_DO_NOT_USE$$"));
63                                if (typed_key<T>::has_default_)
64                                        dummy = typed_key<T>::default_value_as_text_;
65                                std::wstring data = core_->get_string(path, key, dummy);
66                                if (typed_key<T>::has_default_ || data != dummy) {
67                                        T value = boost::lexical_cast<T>(data);
68                                        update_target(&value);
69                                }
70                        }
71                        virtual void notify(settings_impl_interface_ptr core_, std::wstring parent, std::wstring path, std::wstring key) const {
72                                std::wstring dummy(_T("$$DUMMY_VALUE_DO_NOT_USE$$"));
73                                if (typed_key<T>::has_default_)
74                                        dummy = typed_key<T>::default_value_as_text_;
75                                std::wstring data = core_->get_string(parent, key, dummy);
76                                if (typed_key<T>::has_default_ || data != dummy)
77                                        dummy = data;
78                                data = core_->get_string(path, key, dummy);
79                                if (typed_key<T>::has_default_ || data != dummy) {
80                                        T value = boost::lexical_cast<T>(data);
81                                        update_target(&value);
82                                }
83                        }
84                };
85                template<class T>
86                class typed_path_value : public typed_key<T> {
87                public:
88                        typed_path_value(const T& v, bool has_default) : typed_key<T>(v, has_default) {}
89                        virtual NSCAPI::settings_type get_type() const {
90                                return NSCAPI::key_string;
91                        }
92                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path, std::wstring key) const {
93                                std::wstring dummy(_T("$$DUMMY_VALUE_DO_NOT_USE$$"));
94                                if (typed_key<T>::has_default_)
95                                        dummy = typed_key<T>::default_value_as_text_;
96                                std::wstring data = core_->get_string(path, key, dummy);
97                                if (typed_key<T>::has_default_ || data != dummy) {
98                                        T value = boost::lexical_cast<T>(core_->expand_path(data));
99                                        update_target(&value);
100                                }
101                        }
102                        virtual void notify(settings_impl_interface_ptr core_, std::wstring parent, std::wstring path, std::wstring key) const {
103                                std::wstring dummy(_T("$$DUMMY_VALUE_DO_NOT_USE$$"));
104                                if (typed_key<T>::has_default_)
105                                        dummy = typed_key<T>::default_value_as_text_;
106                                std::wstring data = core_->get_string(parent, key, dummy);
107                                if (typed_key<T>::has_default_ || data != dummy)
108                                        dummy = data;
109                                data = core_->get_string(path, key, dummy);
110                                if (typed_key<T>::has_default_ || data != dummy) {
111                                        T value = boost::lexical_cast<T>(core_->expand_path(data));
112                                        update_target(&value);
113                                }
114                        }
115                };
116               
117                template<class T>
118                class typed_int_value : public typed_key<T> {
119                public:
120                        typed_int_value(const T& v, bool has_default) : typed_key<T>(v, has_default), default_value_as_int_(boost::lexical_cast<int>(v)) {}
121                        typed_key<T>* default_value(const T& v) {
122                                typed_key<T>::default_value(v);
123                                default_value_as_int_ = boost::lexical_cast<int>(v);
124                                return this;
125                        }
126                        virtual NSCAPI::settings_type get_type() const {
127                                return NSCAPI::key_integer;
128                        }
129                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path, std::wstring key) const {
130                                int dummy = -1;
131                                if (typed_key<T>::has_default_)
132                                        dummy = default_value_as_int_;
133                                int val = core_->get_int(path, key, dummy);
134                                if (!typed_key<T>::has_default_ && val == dummy) {
135                                        dummy = -2;
136                                        val = core_->get_int(path, key, dummy);
137                                        if (val == dummy)
138                                                return;
139                                }
140                                T value = static_cast<T>(val);
141                                update_target(&value);
142                        }
143                        virtual void notify(settings_impl_interface_ptr core_, std::wstring parent, std::wstring path, std::wstring key) const {
144                                if (typed_key<T>::has_default_) {
145                                        T default_value = static_cast<T>(core_->get_int(parent, key, default_value_as_int_));
146                                        T value = static_cast<T>(core_->get_int(path, key, default_value));
147                                        update_target(&value);
148                                } else {
149                                        int dummy = -1;
150                                        int defval = core_->get_int(path, key, dummy);
151                                        if (defval == dummy) {
152                                                dummy = -2;
153                                                defval = core_->get_int(path, key, dummy);
154                                        }
155                                        if (defval != dummy) {
156                                                T value = static_cast<T>(core_->get_int(path, key, defval));
157                                                update_target(&value);
158                                        }
159                                        dummy = -1;
160                                        int val = core_->get_int(path, key, dummy);
161                                        if (val == dummy) {
162                                                dummy = -2;
163                                                val = core_->get_int(path, key, dummy);
164                                                if (val == dummy)
165                                                        return;
166                                        }
167                                        T value = static_cast<T>(val);
168                                        update_target(&value);
169                                }
170                        }
171                protected:
172                        int default_value_as_int_;
173                };
174                template<class T>
175                class typed_bool_value : public typed_int_value<T> {
176                public:
177                        typed_bool_value(const T& v, bool has_default) : typed_int_value<T>(v, has_default) {}
178                        virtual NSCAPI::settings_type get_type() const {
179                                return NSCAPI::key_bool;
180                        }
181                        // TODO: FIXME: Add support for has_default
182                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path, std::wstring key) const {
183                                T value = static_cast<T>(core_->get_bool(path, key, typed_int_value<T>::default_value_as_int_==1));
184                                update_target(&value);
185                        }
186                        virtual void notify(settings_impl_interface_ptr core_, std::wstring parent, std::wstring path, std::wstring key) const {
187                                T default_value = static_cast<T>(core_->get_bool(parent, key, typed_int_value<T>::default_value_as_int_==1));
188                                T value = static_cast<T>(core_->get_bool(path, key, default_value));
189                                update_target(&value);
190                        }
191                };
192
193                template<class T, class TBase>
194                class typed_key_value : public TBase {
195                public:
196                        typed_key_value(T* store_to, const T& v, bool has_default) : TBase(v, has_default), store_to_(store_to) {}
197
198                        virtual void update_target(T *value) const {
199                                if (store_to_)
200                                        *store_to_ = *value;
201                        }
202                protected:
203                        T* store_to_;
204                };
205
206                template<class T, class V, class TBase>
207                class typed_key_entry_in_vector : public TBase {
208                public:
209                        typed_key_entry_in_vector(V* store_to, typename V::key_type key, const T& v, bool has_default) : TBase(v, has_default), store_to_(store_to), key_(key) {}
210
211                        virtual void update_target(T *value) const {
212                                if (store_to_)
213                                        (*store_to_)[key_] = *value;
214                        }
215                protected:
216                        V* store_to_;
217                        typename V::key_type key_;
218                };
219
220                template<class T, class TBase>
221                class typed_key_fun : public TBase {
222                public:
223                        typed_key_fun(boost::function<void (T)> callback, const T& v, bool has_default): TBase(v, has_default), callback_(callback) {}
224
225                        virtual void update_target(T *value) const {
226                                callback_(*value);
227                        }
228                protected:
229                        boost::function<void (T)> callback_;
230                };
231
232                template<typename T>
233                boost::shared_ptr<typed_key_entry_in_vector<std::wstring, T, typed_string_value<std::wstring> > > wstring_vector_key(T *val, typename T::key_type key, std::wstring def) {
234                        boost::shared_ptr<typed_key_entry_in_vector<std::wstring, T, typed_string_value<std::wstring> > > r(new typed_key_entry_in_vector<std::wstring, T, typed_string_value<std::wstring> >(val, key, def, true));
235                        return r;
236                }
237
238                typedef typed_key_value<std::wstring, typed_string_value<std::wstring> > wstring_key_type;
239                typedef typed_key_value<std::string, typed_string_value<std::string> > string_key_type;
240                typedef typed_key_value<std::wstring, typed_path_value<std::wstring> > wpath_key_type;
241                typedef typed_key_value<unsigned int, typed_int_value<unsigned int> > uint_key_type;
242                typedef typed_key_value<int, typed_int_value<int> > int_key_type;
243                typedef typed_key_value<bool, typed_bool_value<bool> > bool_key_type;
244
245                /*
246                template<typename T>
247                typed_key_entry_in_vector<std::wstring, T, typed_string_value<std::wstring> >* wstring_vector_key(T *val, typename T::key_type key, std::wstring def);
248                */
249                boost::shared_ptr<wstring_key_type> wstring_key(std::wstring *val, std::wstring def);
250                boost::shared_ptr<wstring_key_type> wstring_key(std::wstring *val);
251                boost::shared_ptr<string_key_type> string_key(std::string *val, std::string def);
252                boost::shared_ptr<string_key_type> string_key(std::string *val);
253                boost::shared_ptr<int_key_type> int_key(int *val, int def = 0);
254                boost::shared_ptr<uint_key_type> uint_key(unsigned int *val, unsigned int def);
255                boost::shared_ptr<bool_key_type> bool_key(bool *val, bool def);
256                boost::shared_ptr<bool_key_type> bool_key(bool *val);
257                boost::shared_ptr<wpath_key_type> wpath_key(std::wstring *val, std::wstring def);
258                boost::shared_ptr<wpath_key_type> wpath_key(std::wstring *val);
259
260                template<class T>
261                boost::shared_ptr<typed_key_fun<T, typed_int_value<T> > > int_fun_key(boost::function<void (T)> fun, T def) {
262                        boost::shared_ptr<typed_key_fun<T, typed_int_value<T> > > r(new typed_key_fun<T, typed_int_value<T> >(fun, def, true));
263                        return r;
264                }
265                template<class T>
266                boost::shared_ptr<typed_key_fun<T, typed_int_value<T> > > int_fun_key(boost::function<void (T)> fun) {
267                        boost::shared_ptr<typed_key_fun<T, typed_int_value<T> > > r(new typed_key_fun<T, typed_int_value<T> >(fun, 0, false));
268                        return r;
269                }
270                template<class T>
271                boost::shared_ptr<typed_key_fun<T, typed_bool_value<T> > > bool_fun_key(boost::function<void (T)> fun, T def) {
272                        boost::shared_ptr<typed_key_fun<T, typed_bool_value<T> > > r(new typed_key_fun<T, typed_bool_value<T> >(fun, def, true));
273                        return r;
274                }
275                template<class T>
276                boost::shared_ptr<typed_key_fun<T, typed_string_value<T> > > string_fun_key(boost::function<void (T)> fun, T def) {
277                        boost::shared_ptr<typed_key_fun<T, typed_string_value<T> > > r(new typed_key_fun<T, typed_string_value<T> >(fun, def, true));
278                        return r;
279                }
280                template<class T>
281                boost::shared_ptr<typed_key_fun<T, typed_string_value<T> > > string_fun_key(boost::function<void (T)> fun) {
282                        boost::shared_ptr<typed_key_fun<T, typed_string_value<T> > > r(new typed_key_fun<T, typed_string_value<T> >(fun, T(), false));
283                        return r;
284                }
285
286                class path_interface {
287                public:
288                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path) const = 0;
289                };
290
291                template<class T=std::map<std::wstring,std::wstring> >
292                class typed_path_map : public path_interface {
293                public:
294                        typed_path_map(T* store_to)  : store_to_(store_to) {}
295
296                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path) const {
297                                if (store_to_) {
298                                        std::list<std::wstring> list = core_->get_keys(path);
299                                        T result;
300                                        BOOST_FOREACH(std::wstring key, list) {
301                                                result[key] = core_->get_string(path, key, _T(""));
302                                        }
303                                        *store_to_ = result;
304                                }
305                        }
306
307                protected:
308                        T* store_to_;
309                };
310
311                class typed_path_list : public path_interface {
312                public:
313                        typed_path_list(std::list<std::wstring>* store_to)  : store_to_(store_to) {}
314
315                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path) const {
316                                if (store_to_) {
317                                        *store_to_ = core_->get_keys(path);
318                                }
319                        }
320
321                protected:
322                        std::list<std::wstring>* store_to_;
323                };
324
325                class typed_path_fun_value : public path_interface {
326                public:
327                        typed_path_fun_value(boost::function<void (std::wstring, std::wstring)> callback) : callback_(callback) {}
328
329                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path) const {
330                                if (callback_) {
331                                        std::list<std::wstring> list = core_->get_keys(path);
332                                        BOOST_FOREACH(std::wstring key, list) {
333                                                std::wstring val = core_->get_string(path, key, _T(""));
334                                                callback_(key, val);
335                                        }
336                                        list = core_->get_sections(path);
337                                        BOOST_FOREACH(std::wstring key, list) {
338                                                callback_(key, _T(""));
339                                        }
340                                }
341                        }
342
343                protected:
344                        boost::function<void (std::wstring, std::wstring)> callback_;
345                };
346
347                class typed_path_fun : public path_interface {
348                public:
349                        typed_path_fun(boost::function<void (std::wstring)> callback) : callback_(callback) {}
350
351                        virtual void notify(settings_impl_interface_ptr core_, std::wstring path) const {
352                                if (callback_) {
353                                        std::list<std::wstring> list = core_->get_keys(path);
354                                        BOOST_FOREACH(std::wstring key, list) {
355                                                callback_(key);
356                                        }
357                                }
358                        }
359
360                protected:
361                        boost::function<void (std::wstring)> callback_;
362                };
363
364
365                boost::shared_ptr<typed_path_fun> fun_path(boost::function<void (std::wstring)> fun);
366                boost::shared_ptr<typed_path_fun_value> fun_values_path(boost::function<void (std::wstring,std::wstring)> fun);
367                boost::shared_ptr<typed_path_map<> > wstring_map_path(std::map<std::wstring,std::wstring> *val);
368                boost::shared_ptr<typed_path_list> wstring_list_path(std::list<std::wstring> *val);
369
370                struct description_container {
371                        std::wstring title;
372                        std::wstring description;
373                        bool advanced;
374
375                        description_container(std::wstring title, std::wstring description, bool advanced)
376                                : title(title)
377                                , description(description)
378                                , advanced(advanced)
379                        {}
380                        description_container(std::wstring title, std::wstring description)
381                                : title(title)
382                                , description(description)
383                                , advanced(false)
384                        {}
385
386                        description_container(const description_container& obj) {
387                                title = obj.title;
388                                description = obj.description;
389                                advanced = obj.advanced;
390                        }
391                        description_container& operator=(const description_container& obj) {
392                                title = obj.title;
393                                description = obj.description;
394                                advanced = obj.advanced;
395                                return *this;
396                        }
397
398                };
399
400                struct key_info {
401                        std::wstring path;
402                        std::wstring key_name;
403                        std::wstring parent;
404
405                        boost::shared_ptr<key_interface> key;
406                        description_container description;
407
408                        key_info(std::wstring path_, std::wstring key_name_, boost::shared_ptr<key_interface> key, description_container description_)
409                                : path(path_)
410                                , key_name(key_name_)
411                                , key(key)
412                                , description(description_)
413                        {}
414                        key_info(const key_info& obj) : path(obj.path), key_name(obj.key_name), key(obj.key), description(obj.description), parent(obj.parent) {}
415                        virtual key_info& operator=(const key_info& obj) {
416                                path = obj.path;
417                                key_name = obj.key_name;
418                                key = obj.key;
419                                description = obj.description;
420                                parent = obj.parent;
421                                return *this;
422                        }
423                        void set_parent(std::wstring parent_) {
424                                parent = parent_;
425                        }
426                        bool has_parent() const {
427                                return !parent.empty();
428                        }
429                        std::wstring get_parent() const {
430                                return parent;
431                        }
432                };
433                struct path_info {
434                        std::wstring path_name;
435                        description_container description;
436                        boost::shared_ptr<path_interface> path;
437
438                        path_info(std::wstring path_name, description_container description_) : path_name(path_name), description(description_) {}
439                        path_info(std::wstring path_name, boost::shared_ptr<path_interface> path, description_container description_) : path_name(path_name), path(path), description(description_) {}
440
441                        path_info(const path_info& obj) : path_name(obj.path_name), description(obj.description), path(obj.path) {}
442                        virtual path_info& operator=(const path_info& obj) {
443                                path_name = obj.path_name;
444                                path = obj.path;
445                                description = obj.description;
446                                return *this;
447                        }
448
449                };
450
451                class settings_registry;
452                class settings_paths_easy_init {
453                public:
454                        settings_paths_easy_init(settings_registry* owner) : owner(owner) {}
455                        settings_paths_easy_init(std::wstring path, settings_registry* owner) : path_(path), owner(owner) {}
456
457                        settings_paths_easy_init& operator()(boost::shared_ptr<path_interface> value, std::wstring title, std::wstring description) {
458                                boost::shared_ptr<path_info> d(new path_info(path_, value, description_container(title, description)));
459                                add(d);
460                                return *this;
461                        }
462                        settings_paths_easy_init& operator()(std::wstring title, std::wstring description) {
463                                boost::shared_ptr<path_info> d(new path_info(path_, description_container(title, description)));
464                                add(d);
465                                return *this;
466                        }
467                        settings_paths_easy_init& operator()(std::wstring path, std::wstring title, std::wstring description) {
468                                if (!path_.empty())
469                                        path = path_ + _T("/") + path;
470                                boost::shared_ptr<path_info> d(new path_info(path, description_container(title, description)));
471                                add(d);
472                                return *this;
473                        }
474                        settings_paths_easy_init& operator()(std::wstring path, boost::shared_ptr<path_interface> value, std::wstring title, std::wstring description) {
475                                if (!path_.empty())
476                                        path = path_ + _T("/") + path;
477                                boost::shared_ptr<path_info> d(new path_info(path, value, description_container(title, description)));
478                                add(d);
479                                return *this;
480                        }
481
482                        void add(boost::shared_ptr<path_info> d);
483
484                private:
485                        settings_registry* owner;
486                        std::wstring path_;
487                };     
488
489                class settings_keys_easy_init {
490                public:
491                        settings_keys_easy_init(settings_registry* owner_) : owner(owner_) {}
492                        settings_keys_easy_init(std::wstring path, settings_registry* owner_) : owner(owner_), path_(path) {}
493                        settings_keys_easy_init(std::wstring path, std::wstring parent, settings_registry* owner_) : owner(owner_), path_(path), parent_(parent) {}
494
495                        settings_keys_easy_init& operator()(std::wstring path, std::wstring key_name, boost::shared_ptr<key_interface> value, std::wstring title, std::wstring description, bool advanced = false) {
496                                boost::shared_ptr<key_info> d(new key_info(path, key_name, value, description_container(title, description, advanced)));
497                                if (!parent_.empty())
498                                        d->set_parent(parent_);
499                                add(d);
500                                return *this;
501                        }
502
503                        settings_keys_easy_init& operator()(std::wstring key_name, boost::shared_ptr<key_interface> value, std::wstring title, std::wstring description, bool advanced = false) {
504                                boost::shared_ptr<key_info> d(new key_info(path_, key_name, value, description_container(title, description, advanced)));
505                                if (!parent_.empty())
506                                        d->set_parent(parent_);
507                                add(d);
508                                return *this;
509                        }
510
511                        void add(boost::shared_ptr<key_info> d);
512
513                private:
514                        settings_registry* owner;
515                        std::wstring path_;
516                        std::wstring parent_;
517                };     
518
519
520                class path_extension {
521                public:
522                        path_extension(settings_registry * owner, std::wstring path) : owner_(owner), path_(path) {}
523
524                        settings_keys_easy_init add_key_to_path(std::wstring path) {
525                                return settings_keys_easy_init(get_path(path), owner_);
526                        }
527                        settings_keys_easy_init add_key() {
528                                return settings_keys_easy_init(path_, owner_);
529                        }
530                        settings_paths_easy_init add_path(std::wstring path = _T("")) {
531                                return settings_paths_easy_init(get_path(path), owner_);
532                        }
533                        inline std::wstring get_path(std::wstring path) {
534                                if (!path.empty())
535                                        return path_ + _T("/") + path;
536                                return path_;
537                        }
538
539                private:
540                        std::wstring path_;
541                        settings_registry * owner_;
542                };
543                class alias_extension {
544                public:
545                        alias_extension(settings_registry * owner, std::wstring alias) : owner_(owner), alias_(alias) {}
546                        alias_extension(const alias_extension &other) : owner_(other.owner_), alias_(other.alias_), parent_(other.parent_) {}
547                        alias_extension& operator = (const alias_extension& other) {
548                                owner_ = other.owner_;
549                                alias_ = other.alias_;
550                                parent_ = other.parent_;
551                                return *this;
552                        }
553
554                        settings_keys_easy_init add_key_to_path(std::wstring path) {
555                                return settings_keys_easy_init(get_path(path), parent_, owner_);
556                        }
557                        settings_paths_easy_init add_path(std::wstring path) {
558                                return settings_paths_easy_init(get_path(path), owner_);
559                        }
560                        inline std::wstring get_path(std::wstring path = _T("")) {
561                                if (path.empty())
562                                        return _T("/") + alias_;
563                                return path + _T("/") + alias_;
564                        }
565
566
567                        settings_keys_easy_init add_key_to_settings(std::wstring path = _T("")) {
568                                return settings_keys_easy_init(get_settings_path(path), parent_, owner_);
569                        }
570                        settings_paths_easy_init add_path_to_settings(std::wstring path = _T("")) {
571                                return settings_paths_easy_init(get_settings_path(path), owner_);
572                        }
573                        inline std::wstring get_settings_path(std::wstring path) {
574                                if (path.empty())
575                                        return _T("/settings/") + alias_;
576                                return _T("/settings/") + alias_ + _T("/") + path;
577                        }
578
579                        alias_extension add_parent(std::wstring parent_path) {
580                                set_parent_path(parent_path);
581                                return *this;
582                        }
583
584
585                        static std::wstring get_alias(std::wstring cur, std::wstring def) {
586                                if (cur.empty())
587                                        return def;
588                                else
589                                        return cur;
590                        }
591                        static std::wstring get_alias(std::wstring prefix, std::wstring cur, std::wstring def) {
592                                if (!prefix.empty())
593                                        prefix += _T("/");
594                                if (cur.empty())
595                                        return prefix + def;
596                                else
597                                        return prefix + cur;
598                        }
599                        void set_alias(std::wstring cur, std::wstring def) {
600                                alias_ = get_alias(cur, def);
601                        }
602                        void set_alias(std::wstring prefix, std::wstring cur, std::wstring def) {
603                                alias_ = get_alias(prefix, cur, def);
604                        }
605                        void set_parent_path(std::wstring parent) {
606                                parent_ = parent;
607                        }
608
609                private:
610                        std::wstring alias_;
611                        settings_registry * owner_;
612                        std::wstring parent_;
613                };
614
615                class settings_registry {
616                        typedef std::list<boost::shared_ptr<key_info> > key_list;
617                        typedef std::list<boost::shared_ptr<path_info> > path_list;
618                        key_list keys_;
619                        path_list paths_;
620                        settings_impl_interface_ptr core_;
621                        std::wstring alias_;
622                public:
623                        settings_registry(settings_impl_interface_ptr core) : core_(core) {}
624                        void add(boost::shared_ptr<key_info> info) {
625                                keys_.push_back(info);
626                        }
627                        void add(boost::shared_ptr<path_info> info) {
628                                paths_.push_back(info);
629                        }
630
631                        settings_keys_easy_init add_key() {
632                                return settings_keys_easy_init(this);
633                        }
634                        settings_keys_easy_init add_key_to_path(std::wstring path) {
635                                return settings_keys_easy_init(path, this);
636                        }
637                        settings_keys_easy_init add_key_to_settings(std::wstring path) {
638                                return settings_keys_easy_init(_T("/settings/") + path, this);
639                        }
640                        settings_paths_easy_init add_path() {
641                                return settings_paths_easy_init(this);
642                        }
643                        settings_paths_easy_init add_path_to_settings() {
644                                return settings_paths_easy_init(_T("/settings"), this);
645                        }
646
647                        void set_alias(std::wstring cur, std::wstring def) {
648                                alias_ = alias_extension::get_alias(cur, def);
649                        }
650                        void set_alias(std::wstring prefix, std::wstring cur, std::wstring def) {
651                                alias_ = alias_extension::get_alias(prefix, cur, def);
652                        }
653                        void set_alias(std::wstring alias) {
654                                alias_ = alias;
655                        }
656                        alias_extension alias() {
657                                return alias_extension(this, alias_);
658                        }
659                        alias_extension alias(std::wstring alias) {
660                                return alias_extension(this, alias);
661                        }
662                        alias_extension alias(std::wstring cur, std::wstring def) {
663                                return alias_extension(this, alias_extension::get_alias(cur, def));
664                        }
665                        alias_extension alias(std::wstring prefix, std::wstring cur, std::wstring def) {
666                                return alias_extension(this, alias_extension::get_alias(prefix, cur, def));
667                        }
668
669                        path_extension path(std::wstring path) {
670                                return path_extension(this, path);
671                        }
672                       
673
674                        void register_all() {
675                                BOOST_FOREACH(key_list::value_type v, keys_) {
676                                        if (v->key) {
677                                                //std::wcout << _T("Setting: ") << v->key_name << _T(" ===> ") << v->parent << std::endl;
678                                                std::wstring desc = v->description.description;
679                                                if (v->has_parent()) {
680                                                        desc += _T(" Parent element can be found under: ") + v->parent;
681                                                        core_->register_key(v->parent, v->key_name, v->key->get_type(), v->description.title, desc, v->key->get_default_as_string(), v->description.advanced);
682                                                }
683                                                core_->register_key(v->path, v->key_name, v->key->get_type(), v->description.title, desc, v->key->get_default_as_string(), v->description.advanced);
684                                        }
685                                }
686                                BOOST_FOREACH(path_list::value_type v, paths_) {
687                                        core_->register_path(v->path_name, v->description.title, v->description.description, v->description.advanced);
688                                }
689                        }
690                        void clear() {
691                                keys_.clear();
692                                paths_.clear();
693                        }
694
695                        void notify() {
696                                BOOST_FOREACH(key_list::value_type v, keys_) {
697                                        try {
698                                                if (v->key) {
699                                                        if (v->has_parent())
700                                                                v->key->notify(core_, v->parent, v->path, v->key_name);
701                                                        else
702                                                                v->key->notify(core_, v->path, v->key_name);
703                                                }
704                                        } catch (const std::exception &e) {
705                                                core_->err(__FILE__, __LINE__, _T("Failed to notify ") + v->key_name + _T(": ") + utf8::cvt<std::wstring>(e.what()));
706                                        } catch (...) {
707                                                core_->err(__FILE__, __LINE__, _T("Failed to notify: ") + v->key_name);
708                                        }
709                                }
710                                BOOST_FOREACH(path_list::value_type v, paths_) {
711                                        try {
712                                                if (v->path)
713                                                        v->path->notify(core_, v->path_name);
714                                        } catch (const std::exception &e) {
715                                                core_->err(__FILE__, __LINE__, _T("Failed to notify ") + v->path_name + _T(": ") + utf8::cvt<std::wstring>(e.what()));
716                                        } catch (...) {
717                                                core_->err(__FILE__, __LINE__, _T("Failed to notify: ") + v->path_name);
718                                        }
719                                }
720
721                        }
722                };
723        }
724}
Note: See TracBrowser for help on using the repository browser.