diff options
author | randomdan <randomdan@localhost> | 2011-10-19 00:46:42 +0000 |
---|---|---|
committer | randomdan <randomdan@localhost> | 2011-10-19 00:46:42 +0000 |
commit | 25d5ef8588cee272c78c7e83960ab889c1fd7ce0 (patch) | |
tree | 69729d7f7d9f8cf050418a605d883e2bdef29456 | |
parent | Adds the JSON and CouchDB module (diff) | |
download | project2-25d5ef8588cee272c78c7e83960ab889c1fd7ce0.tar.bz2 project2-25d5ef8588cee272c78c7e83960ab889c1fd7ce0.tar.xz project2-25d5ef8588cee272c78c7e83960ab889c1fd7ce0.zip |
Remove session implementations per container, not point
-rw-r--r-- | project2/cgi/cgiAppEngine.cpp | 18 | ||||
-rw-r--r-- | project2/common/session.cpp | 39 | ||||
-rw-r--r-- | project2/common/session.h | 19 | ||||
-rw-r--r-- | project2/common/sessionContainer.cpp | 6 | ||||
-rw-r--r-- | project2/common/sessionContainer.h | 1 | ||||
-rw-r--r-- | project2/console/consoleAppEngine.cpp | 43 | ||||
-rw-r--r-- | project2/json/couchSession.cpp | 61 | ||||
-rw-r--r-- | project2/xml/sessionXml.cpp | 106 | ||||
-rw-r--r-- | project2/xml/sessionXml.h | 1 |
9 files changed, 110 insertions, 184 deletions
diff --git a/project2/cgi/cgiAppEngine.cpp b/project2/cgi/cgiAppEngine.cpp index 1cee535..0f15f89 100644 --- a/project2/cgi/cgiAppEngine.cpp +++ b/project2/cgi/cgiAppEngine.cpp @@ -138,6 +138,16 @@ CgiApplicationEngine::addEnvData(const Presenter * p) const p->popSub(); } +static +void +addToPresenter(const Environment * env, const Presenter * p, const Glib::ustring & name, const VariableType & value) +{ + p->pushSub("var", env->xmlPrefix); + p->addAttr("value", value); + p->addAttr("name", name); + p->popSub(); +} + void CgiApplicationEngine::addAppData(const Presenter * p) const { @@ -145,13 +155,7 @@ CgiApplicationEngine::addAppData(const Presenter * p) const // Sessions variables p->pushSub("session", env()->xmlPrefix); p->addAttr("id", cursession->ID.str()); - Session::Values session(cursession->GetValuesCopy()); - BOOST_FOREACH(Session::Values::value_type sv, session) { - p->pushSub("var", env()->xmlPrefix); - p->addAttr("value", sv.second); - p->addAttr("name", sv.first); - p->popSub(); - } + cursession->ForeachValue(boost::bind(addToPresenter, env(), p, _1, _2)); p->popSub(); // Timing info diff --git a/project2/common/session.cpp b/project2/common/session.cpp index d796f83..fcfd3ca 100644 --- a/project2/common/session.cpp +++ b/project2/common/session.cpp @@ -1,5 +1,6 @@ #include <pch.hpp> #include "session.h" +#include "safeMapFind.h" Session::Session(const UUID & sid) : ID(sid) @@ -10,3 +11,41 @@ Session::~Session() { } +void +Session::ExpiryTime(time_t t) +{ + expires = t; +} + +time_t +Session::ExpiryTime() const +{ + return expires; +} + +VariableType +Session::GetValue(const Glib::ustring & name) const +{ + return safeMapFind<VariableNotFound>(vars, name)->second; +} + +void +Session::SetValue(const Glib::ustring & name, const VariableType & value) +{ + vars[name] = value; +} + +void +Session::ClearValue(const Glib::ustring & name) +{ + vars.erase(name); +} + +void +Session::ForeachValue(const Session::SVH & svh) const +{ + BOOST_FOREACH(const Values::value_type & v, vars) { + svh(v.first, v.second); + } +} + diff --git a/project2/common/session.h b/project2/common/session.h index ea72c54..6aba83c 100644 --- a/project2/common/session.h +++ b/project2/common/session.h @@ -5,6 +5,7 @@ #include <map> #include <glibmm/ustring.h> #include <boost/intrusive_ptr.hpp> +#include <boost/function.hpp> #include "intrusivePtrBase.h" #include "variables.h" #include "exceptions.h" @@ -14,21 +15,25 @@ class Session : public virtual IntrusivePtrBase { public: SimpleMessageException(VariableNotFound); typedef std::map<Glib::ustring, VariableType> Values; + typedef boost::function2<void, const Glib::ustring &, const VariableType &> SVH; Session(const UUID & id); - virtual ~Session() = 0; + virtual ~Session(); - virtual VariableType GetValue(const Glib::ustring & name) const = 0; - virtual Values GetValuesCopy() const = 0; - virtual void SetValue(const Glib::ustring & name, const VariableType & value) = 0; - virtual void ClearValue(const Glib::ustring & name) = 0; - virtual time_t ExpiryTime() const = 0; + VariableType GetValue(const Glib::ustring & name) const; + void ForeachValue(const SVH &) const; + void SetValue(const Glib::ustring & name, const VariableType & value); + void ClearValue(const Glib::ustring & name); + time_t ExpiryTime() const; const UUID ID; protected: - virtual void ExpiryTime(time_t) = 0; + void ExpiryTime(time_t); friend class SessionContainer; + + Values vars; + time_t expires; }; typedef boost::intrusive_ptr<Session> SessionPtr; diff --git a/project2/common/sessionContainer.cpp b/project2/common/sessionContainer.cpp index 1acd6d0..82b7ca8 100644 --- a/project2/common/sessionContainer.cpp +++ b/project2/common/sessionContainer.cpp @@ -18,3 +18,9 @@ SessionContainer::GetSession(const UUID & id) const return s; } +SessionPtr +SessionContainer::newSession() const +{ + return new Session(UUID::generate_random()); +} + diff --git a/project2/common/sessionContainer.h b/project2/common/sessionContainer.h index ffbc5ed..1ee7689 100644 --- a/project2/common/sessionContainer.h +++ b/project2/common/sessionContainer.h @@ -15,6 +15,7 @@ class SessionContainer : public IntrusivePtrBase { protected: virtual SessionPtr getSession(const UUID & sid) const = 0; + SessionPtr newSession() const; }; typedef boost::intrusive_ptr<SessionContainer> SessionContainerPtr; diff --git a/project2/console/consoleAppEngine.cpp b/project2/console/consoleAppEngine.cpp index f2dcaa8..e49825f 100644 --- a/project2/console/consoleAppEngine.cpp +++ b/project2/console/consoleAppEngine.cpp @@ -10,47 +10,6 @@ SimpleMessageException(UnknownPlatformAlias); -/// Session implementation that stores its contents locally in memory, it has no long term persistence -class ConsoleSession : public Session { - public: - ConsoleSession() : Session(UUID::generate_random()), expiry(0) - { - } - virtual ~ConsoleSession() - { - } - - virtual VariableType GetValue(const Glib::ustring & name) const - { - return safeMapFind<VariableNotFound>(vars, name)->second; - } - virtual Values GetValuesCopy() const - { - return vars; - } - virtual void SetValue(const Glib::ustring & name, const VariableType & value) - { - vars[name] = value; - } - virtual void ClearValue(const Glib::ustring & name) - { - vars.erase(name); - } - virtual time_t ExpiryTime() const - { - return expiry; - } - - protected: - virtual void ExpiryTime(time_t t) - { - expiry = t; - } - private: - time_t expiry; - Values vars; -}; - ConsoleApplicationEngine::ConsoleApplicationEngine(const ConsoleEnvironment * env, const boost::filesystem::path & f) : XmlScriptParser(f, false), SourceObject(get_document()->get_root_node()), @@ -59,7 +18,7 @@ ConsoleApplicationEngine::ConsoleApplicationEngine(const ConsoleEnvironment * en TaskHost(f), ViewHost(f), _env(env), - runtime(new ConsoleSession()) + runtime(new Session(UUID::generate_random())) { } diff --git a/project2/json/couchSession.cpp b/project2/json/couchSession.cpp index d2eeca2..c6a15c0 100644 --- a/project2/json/couchSession.cpp +++ b/project2/json/couchSession.cpp @@ -13,42 +13,6 @@ #include "conversion.h" #include <boost/program_options.hpp> -class CouchSession : public Session { - public: - CouchSession(const UUID & sid) : Session(sid) { - } - CouchSession(const UUID & sid, const json::Object & o) : Session(sid), obj(o) { - } - virtual VariableType GetValue(const Glib::ustring & name) const { - return boost::apply_visitor(JsonToProject2(), *safeMapFind<VariableNotFound>(obj, name)->second); - } - virtual Values GetValuesCopy() const { - Values vs; - BOOST_FOREACH(const json::Object::value_type & v, obj) { - vs.insert(Values::value_type(v.first, boost::apply_visitor(JsonToProject2(), *v.second))); - } - return vs; - } - virtual void SetValue(const Glib::ustring & name, const VariableType & v) { - obj[name] = json::ValuePtr(new json::Value(boost::apply_visitor(Project2ToJson(), v))); - } - virtual void ClearValue(const Glib::ustring & name) { - obj.erase(name); - } - virtual time_t ExpiryTime() const { - return boost::get<json::Number>(*safeMapFind<VariableNotFound>(obj, ExpiryKey)->second); - } - virtual void ExpiryTime(time_t t) { - obj[ExpiryKey] = json::ValuePtr(new json::Value(json::Number(t))); - } - private: - json::Object obj; - friend class CouchSessionContainer; - friend class CustomCouchSessionLoader; - static const Glib::ustring ExpiryKey; -}; -const Glib::ustring CouchSession::ExpiryKey("project2:expires"); - class CouchDBFailure : public std::exception { }; class CouchSessionContainer : public SessionContainer { @@ -57,21 +21,28 @@ class CouchSessionContainer : public SessionContainer { } virtual SessionPtr getSession(const UUID & uuid) const { try { - SessionPtr s = new CouchSession(uuid, getSessionFromServer(uuid)); - if (s->ExpiryTime() > time(NULL)) { + json::Object obj = getSessionFromServer(uuid); + if (boost::get<json::Number>(*safeMapFind<Session::VariableNotFound>(obj, ExpiryKey)->second) > time(NULL)) { + SessionPtr s = new Session(uuid); + BOOST_FOREACH(const json::Object::value_type & v, obj) { + s->SetValue(v.first, boost::apply_visitor(JsonToProject2(), *v.second)); + } return s; } } catch (...) { } - return new CouchSession(UUID::generate_random()); + return newSession(); } virtual void SaveSession(SessionPtr s) const { CurlPtr c = new Curl(); c->setopt(CURLOPT_UPLOAD, 1L); c->setopt(CURLOPT_FAILONERROR, 1); - Glib::ustring out = json::serializeObject(boost::dynamic_pointer_cast<CouchSession>(s)->obj); + json::Object obj; + s->ForeachValue(boost::bind(&CouchSessionContainer::addToObject, &obj, _1, _2)); + obj[ExpiryKey] = json::ValuePtr(new json::Value((json::Number)s->ExpiryTime())); + Glib::ustring out = json::serializeObject(obj); c->setopt(CURLOPT_INFILESIZE_LARGE, (curl_off_t)out.size()); unsigned int off = 0; BOOST_FOREACH(const std::string & b, baseUrls) { @@ -103,6 +74,11 @@ class CouchSessionContainer : public SessionContainer { throw CouchDBFailure(); } + private: + static void addToObject(json::Object * obj, const Glib::ustring & name, const VariableType & value) { + (*obj)[name] = json::ValuePtr(new json::Value(boost::apply_visitor(Project2ToJson(), value))); + } + static size_t send(Glib::ustring * buf, unsigned int * off, char * str, size_t l) { size_t len = std::min(buf->size() - *off, l); memcpy(str, buf->c_str() + *off, len); @@ -123,8 +99,11 @@ class CouchSessionContainer : public SessionContainer { } static std::vector<std::string> baseUrls; + static const Glib::ustring ExpiryKey; + friend class CustomCouchSessionLoader; }; std::vector<std::string> CouchSessionContainer::baseUrls; +const Glib::ustring CouchSessionContainer::ExpiryKey("project2:expires"); namespace po = boost::program_options; class CustomCouchSessionLoader : public SessionContainerLoaderImpl<CouchSessionContainer> { @@ -167,7 +146,7 @@ class CustomCouchSessionLoader : public SessionContainerLoaderImpl<CouchSessionC json::Object map; Buffer mapBuf; mapBuf.appendf("function(doc) { var exp = doc['%s']; if (exp < (new Date().getTime() / 1000)) { emit(exp, doc._rev); } }", - CouchSession::ExpiryKey.c_str()); + CouchSessionContainer::ExpiryKey.c_str()); map["map"] = json::ValuePtr(new json::Value(mapBuf.str())); Glib::ustring mapStr(json::serializeObject(map)); // Create the CURL handle diff --git a/project2/xml/sessionXml.cpp b/project2/xml/sessionXml.cpp index fc77de2..3fb925f 100644 --- a/project2/xml/sessionXml.cpp +++ b/project2/xml/sessionXml.cpp @@ -10,27 +10,6 @@ #include <boost/lexical_cast.hpp> #include <boost/program_options.hpp> -/// Session implementation that stores its contents in an XML file on the local filesystem -class SessionXml : public Session { - public: - SessionXml(const UUID & sid); - SessionXml(const xmlpp::Element *); - virtual ~SessionXml(); - - VariableType GetValue(const Glib::ustring & name) const; - Values GetValuesCopy() const; - void SetValue(const Glib::ustring & name, const VariableType & value); - void ClearValue(const Glib::ustring & name); - time_t ExpiryTime() const; - void ExpiryTime(time_t); - - private: - Values vars; - time_t expires; - - friend class SessionContainerXml; -}; - namespace po = boost::program_options; class CustomSessionContainerLoaderXml : public SessionContainerLoaderImpl<SessionContainerXml> { public: @@ -63,6 +42,15 @@ SessionContainerXml::~SessionContainerXml() { } +static +void +appendToXmlNode(xmlpp::Element * sess, const Glib::ustring & name, const VariableType & value) +{ + xmlpp::Element * v = sess->add_child("var"); + v->add_child_text(value); + v->set_attribute("name", name); +} + void SessionContainerXml::SaveSession(SessionPtr currentSession) const { @@ -86,11 +74,7 @@ SessionContainerXml::SaveSession(SessionPtr currentSession) const xmlpp::Element * sess = doc->get_root_node()->add_child("session"); sess->set_attribute("id", currentSession->ID.str()); sess->set_attribute("expires", boost::lexical_cast<Glib::ustring>(currentSession->ExpiryTime())); - BOOST_FOREACH(const Session::Values::value_type & nvp, currentSession->GetValuesCopy()) { - xmlpp::Element * v = sess->add_child("var"); - v->add_child_text(nvp.second); - v->set_attribute("name", nvp.first); - } + currentSession->ForeachValue(boost::bind(appendToXmlNode, sess, _1, _2)); doc->write_to_file(xmlFile); if (!parser) { delete doc; @@ -108,69 +92,19 @@ SessionContainerXml::getSession(const UUID & sid) const sid.str().c_str(), time(NULL)); xmlpp::NodeSet sess = sessions.get_document()->get_root_node()->find(xpath); if (sess.size() == 1) { - return new SessionXml(dynamic_cast<const xmlpp::Element *>(sess[0])); + if (const xmlpp::Element * elem = dynamic_cast<const xmlpp::Element *>(sess[0])) { + SessionPtr s = new Session(UUID(elem->get_attribute_value("id"))); + BOOST_FOREACH(const xmlpp::Node * n, elem->find("var")) { + if (const xmlpp::Element * e = dynamic_cast<const xmlpp::Element *>(n)) { + s->SetValue(e->get_attribute_value("name"), e->get_child_text() ? e->get_child_text()->get_content() : ""); + } + } + return s; + } } } catch (...) { } - return new SessionXml(UUID::generate_random()); -} - -SessionXml::SessionXml(const UUID & sid) : - Session(sid) -{ -} - -SessionXml::SessionXml(const xmlpp::Element * p) : - Session(UUID(p->get_attribute_value("id"))), - expires(boost::lexical_cast<time_t>(p->get_attribute_value("expires"))) -{ - xmlpp::NodeSet xvars = p->find("var"); - BOOST_FOREACH(const xmlpp::Node * n, xvars) { - const xmlpp::Element * e = dynamic_cast<const xmlpp::Element *>(n); - if (e) { - vars[e->get_attribute_value("name")] = e->get_child_text() ? e->get_child_text()->get_content() : ""; - } - } -} - -SessionXml::~SessionXml() -{ -} - -void -SessionXml::ExpiryTime(time_t t) -{ - expires = t; -} - -time_t -SessionXml::ExpiryTime() const -{ - return expires; -} - -VariableType -SessionXml::GetValue(const Glib::ustring & name) const -{ - return safeMapFind<VariableNotFound>(vars, name)->second; -} - -void -SessionXml::SetValue(const Glib::ustring & name, const VariableType & value) -{ - vars[name] = value; -} - -void -SessionXml::ClearValue(const Glib::ustring & name) -{ - vars.erase(name); -} - -Session::Values -SessionXml::GetValuesCopy() const -{ - return vars; + return newSession(); } diff --git a/project2/xml/sessionXml.h b/project2/xml/sessionXml.h index 8ba6ae2..2679bff 100644 --- a/project2/xml/sessionXml.h +++ b/project2/xml/sessionXml.h @@ -4,7 +4,6 @@ #include "sessionContainer.h" #include <map> -class SessionXml; class SessionContainerXml : public SessionContainer { public: SessionContainerXml(); |