Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00035 #ifndef KEYVALUE_KEY_MAP_OBJECTMAP_H_
00036 #define KEYVALUE_KEY_MAP_OBJECTMAP_H_
00037
00038 #include <boost/utility.hpp>
00039
00040 #include "keyvalue/extern/String.h"
00041 #include "keyvalue/frontend/LexicalToolKit.h"
00042 #include "keyvalue/mngt/BuilderFrom.h"
00043 #include "keyvalue/mngt/DataSet.h"
00044 #include "keyvalue/mngt/ProcessorMngr.h"
00045 #include "keyvalue/mngt/Repository.h"
00046 #include "keyvalue/sys/exception/Exception.h"
00047 #include "keyvalue/sys/exception/KV_ASSERT.h"
00048 #include "keyvalue/util/Global.h"
00049 #include "keyvalue/value/Variant.h"
00050
00051 namespace keyvalue {
00052 namespace key {
00053
00074 template <typename ObjectType>
00075 class ObjectMap :
00076
00077 private ::boost::noncopyable {
00078
00079 public:
00080
00081 typedef typename value::PtrTraits<ObjectType>::Type_ OutputType_;
00082
00090 OutputType_
00091 map(const value::Variant& variant) const;
00092
00093 private:
00094
00100 virtual string
00101 getName() const = 0;
00102
00103 };
00104
00105
00106
00107
00108
00109 template <typename ObjectType>
00110 typename ObjectMap<ObjectType>::OutputType_
00111 ObjectMap<ObjectType>::map(const value::Variant& variant) const {
00112
00113 string name;
00114
00115
00116
00117 if (variant.is<string>(frontend::LexicalToolKit::input)) {
00118
00119 name = variant.get<string>(frontend::LexicalToolKit::input);
00120
00121 try {
00122 shared_ptr<const DataSet>
00123 data(util::Global<Repository>::get()->getDataSet(name));
00124 return data->build<ObjectType>();
00125 }
00126
00127 catch(Repository::NotFound& error) {
00128 if (error.getName() != name)
00129 throw;
00130 }
00131 }
00132
00133
00134
00135 const AbstractBuilder* const builder =
00136 util::Global<ProcessorMngr>::get()->findBuilder(typeid(ObjectType));
00137
00138 if (!builder) {
00139 if (name.empty())
00140 throw RuntimeError() & "No builder can build object expected by key "
00141 "'" & getName() & "'. (Value is '" & variant & "'.)";
00142 else
00143 throw RuntimeError() & "No object named '" & name & "' exists and no "
00144 "builder can build object expected by key '" & getName() & "' from "
00145 "this string.";
00146 }
00147
00148 typedef BuilderFrom<ObjectType, value::Variant> const BuilderFromVariant;
00149
00150 const BuilderFromVariant* bfv(dynamic_cast<BuilderFromVariant*>(builder));
00151
00152 if (!bfv)
00153 throw RuntimeError() & "Builder '" & builder->getName() & "' needs a "
00154 "data set. It cannot satisfy key '" & getName() & "' and build from "
00155 "input '" & variant & "'.";
00156
00157 return bfv->getObject(variant);
00158 }
00159
00160 }
00161 }
00162
00163 #endif // KEYVALUE_KEY_MAP_OBJECTMAP_H_