00001
00002
00003
00004 #ifndef XMLPERSISTENCE_H
00005 #define XMLPERSISTENCE_H
00006
00007
00008
00009 #include "facilities/error.h"
00010 #include <dom/DOM_Element.hpp>
00011 #include "xml/Dom.h"
00012 #include <string>
00013 #include <iostream>
00014 #include <iterator>
00015 #include <vector>
00016 #include <map>
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 class DOM_Element;
00034
00035 namespace xml {
00036 class PersistentObject {
00037 public:
00038
00039 typedef std::string _PersistKey;
00040 class _Factory {
00041 public:
00042 virtual PersistentObject* create(const DOM_Element&);
00043 };
00044
00045
00046 PersistentObject() {}
00047
00048
00049 static PersistentObject* createPersistence (const DOM_Element&);
00050
00051 static bool addPersistence(const _PersistKey&,
00052 class PersistentObject::_Factory* );
00053
00054 static void killPersistence ();
00055
00056
00057 bool operator==(const PersistentObject&) { return true; }
00058
00059
00060
00061
00062
00063
00064 virtual DOM_Element persist(DOM_Element& parent) const;
00065
00066 protected:
00067
00068 PersistentObject(DOM_Element&);
00069
00070
00071 virtual const _PersistKey& persistKey() const = 0;
00072
00073
00074 friend class PersistentObject::_Factory;
00075
00076 private:
00077 static std::map<_PersistKey, class _Factory*>* s_persist_table;
00078 };
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090 template <class _Cont> class PersistentContainer {
00091 public:
00092
00093 PersistentContainer() {}
00094
00095 PersistentContainer(const DOM_Element&);
00096
00097 virtual ~PersistentContainer() {}
00098
00099 typedef _Cont container;
00100 typedef typename container::iterator iterator;
00101 typedef typename container::const_iterator const_iterator;
00102 typedef typename container::reverse_iterator reverse_iterator;
00103 typedef typename container::const_reverse_iterator const_reverse_iterator;
00104 typedef typename container::value_type value_type;
00105
00106
00107 iterator begin () { return m_container.begin(); }
00108 iterator end () { return m_container.end(); }
00109 const_iterator begin () const { return m_container.begin(); }
00110 const_iterator end () const { return m_container.end(); }
00111 reverse_iterator rbegin () { return m_container.rbegin(); }
00112 reverse_iterator rend () { return m_container.rend(); }
00113 const_reverse_iterator rbegin () const { return m_container.rbegin(); }
00114 const_reverse_iterator rend () const { return m_container.rend(); }
00115 container& operator() (void) { return m_container; }
00116 const container& operator() (void) const { return m_container; }
00117 unsigned int size () const { return m_container.size(); }
00118 bool empty () const { return m_container.empty(); }
00119
00120
00121 iterator insert ( iterator& i, value_type& v )
00122 { return m_container.insert(i,v); }
00123
00126 void load (const DOM_Element&);
00127
00128
00131 virtual void persist(DOM_Element& parent) const;
00132
00133 protected:
00134
00135 private:
00136 container m_container;
00137 };
00138
00139
00140
00141
00142 template <class _Iterator, class _Persistence>
00143 class persist_iterator {
00144 public:
00145
00146 typedef _Iterator iterator;
00147 typedef typename iterator::value_type value_type;
00148 typedef _Persistence persistence;
00149
00150 explicit persist_iterator ( iterator& it );
00151
00152 persist_iterator& operator=(persistence& p);
00153
00154 persist_iterator& operator* ();
00155 persist_iterator& operator++ ();
00156 persist_iterator& operator ++ (int);
00157
00158 private:
00159 iterator& m_iter;
00160 };
00161
00162
00163
00164
00165
00166 inline PersistentObject*
00167 PersistentObject::createPersistence(const DOM_Element& elem) {
00168 std::string temp_string(Dom::transToChar(elem.getTagName()));
00169 _PersistKey key(temp_string);
00170 if (!s_persist_table) FATAL("Persistence information not initialized.");
00171
00172
00173 std::map<_PersistKey, _Factory*>::iterator mit =
00174 s_persist_table->find(key);
00175
00176 if (mit != s_persist_table->end()) {
00177 return (*mit).second->create(elem);
00178 }
00179 else return 0;
00180 }
00181
00182
00183
00184
00185 inline void PersistentObject::killPersistence() {
00186 if (!s_persist_table) return;
00187 for (std::map<_PersistKey, _Factory*>::iterator it =
00188 s_persist_table->begin(); it != s_persist_table->end(); ++it) {
00189 delete (*it).second;
00190 }
00191 }
00192
00193
00194 template <class _Cont>
00195 inline void PersistentContainer<_Cont>::persist(DOM_Element& parent) const
00196 {
00197
00198
00199 for (const_reverse_iterator it = rbegin(); it != rend(); ++it) {
00200 (*it)->persist(parent);
00201 }
00202 }
00203
00204 template <class _Cont>
00205 inline void PersistentContainer<_Cont>::load(const DOM_Element& elem) {
00206 DOM_NodeList children = elem.getChildNodes();
00207 int len = children.getLength();
00208 int iChild;
00209 iterator thisIt = begin();
00210
00211 for (iChild = 0; iChild < len; iChild++) {
00212 if (children.item(iChild).getNodeType() == DOM_Node::ELEMENT_NODE) {
00213 DOM_Node child_tmp = children.item(iChild);
00214 DOM_Element child = DOM_Element(static_cast<DOM_Element&>(child_tmp));
00215
00216 value_type newObj =
00217 static_cast<value_type> (PersistentObject::createPersistence(child));
00218 if (newObj) thisIt = insert(thisIt, newObj);
00219 }
00220 }
00221 }
00222
00223
00224 template <class _Iterator, class _Persistence>
00225 inline persist_iterator<_Iterator, _Persistence>::persist_iterator
00226 (persist_iterator<_Iterator, _Persistence>::iterator& it)
00227 : m_iter(it) {}
00228
00229 template <class _Iterator, class _Persistence>
00230 inline persist_iterator<_Iterator, _Persistence>&
00231 persist_iterator<_Iterator, _Persistence>::operator=
00232 (persist_iterator<_Iterator, _Persistence>::persistence& p) {
00233 value_type* o = value_type::createPersistence(p);
00234 if (o != 0) {
00235 *m_iter = o;
00236 ++m_iter;
00237 }
00238 return *this;
00239 }
00240
00241 template <class _Iterator, class _Persistence>
00242 inline persist_iterator<_Iterator, _Persistence>&
00243 persist_iterator<_Iterator, _Persistence>::operator* () {
00244 return *this;
00245 }
00246
00247 template <class _Iterator, class _Persistence>
00248 inline persist_iterator<_Iterator, _Persistence>&
00249 persist_iterator<_Iterator, _Persistence>::operator++ () {
00250 return *this;
00251 }
00252
00253 template <class _Iterator, class _Persistence>
00254 inline persist_iterator<_Iterator, _Persistence>&
00255 persist_iterator<_Iterator, _Persistence>::operator++ (int) {
00256 return *this;
00257 }
00258 }
00259 #endif // _H_PERSISTENCEHEADER