8 #include <pugixml/pugixml.hpp>
12 #include "ifmap/ifmap_log_types.h"
19 static const char *
NodeName(
const xml_node &node) {
20 const char *name = node.name();
22 const char *dot = strchr(name,
':');
30 ModuleMap::iterator loc = module_map_.find(module);
31 if (loc != module_map_.end()) {
35 module_map_.insert(make_pair(module, parser));
40 ModuleMap::iterator loc = module_map_.find(module);
41 if (loc == module_map_.end()) {
46 module_map_.erase(loc);
51 pair<MetadataParseMap::iterator, bool> result =
52 metadata_map_.insert(make_pair(metadata, parser));
53 assert(result.second);
57 metadata_map_.clear();
58 DeleteInstance(module);
62 string id(node.attribute(
"name").value());
77 MetadataParseMap::const_iterator loc = metadata_map_.find(name);
78 if (loc == metadata_map_.end()) {
81 std::unique_ptr<AutogenProperty> pvalue;
82 bool success = (loc->second)(node, &pvalue);
88 result->
data.reset(data);
91 data->
content.reset(pvalue.release());
98 size_t ns =
id.find(
"contrail:");
99 size_t start = (ns == 0) ?
sizeof(
"contrail:") - 1: 0;
100 size_t loc =
id.find(
':', start);
101 if (loc != string::npos) {
102 *id_type = string(
id, start, loc - start);
103 *id_name = string(
id, loc + 1,
id.size() - (loc + 1));
114 if (src_key != NULL) {
119 request->
key.reset(dst_key);
129 request->
data.reset(dst_data);
135 const xml_node &parent,
bool add_change,
RequestList *list)
const {
136 unique_ptr<DBRequest> request(
new DBRequest);
142 bool has_meta =
false;
143 for (xml_node node = parent.first_child(); node;
144 node = node.next_sibling()) {
146 if (strcmp(name,
"identity") == 0) {
151 request->key.reset(key);
156 request->data.reset(data);
165 if (strcmp(name,
"metadata") == 0) {
170 for (xml_node meta = node.first_child(); meta;
171 meta = meta.next_sibling()) {
172 if (ParseMetadata(meta, request.get())) {
173 SetOrigin(request.get());
175 if (meta.next_sibling()) {
178 list->push_back(current);
184 if (idcount == 0 || !has_meta) {
191 const xml_document &xdoc,
RequestList *list)
const {
192 xml_node current = xdoc.first_child();
195 if (strcmp(
NodeName(current),
"updateResult") == 0 ||
196 strcmp(
NodeName(current),
"searchResult") == 0 ||
197 strcmp(
NodeName(current),
"deleteResult") == 0) {
199 if (strcmp(
NodeName(current),
"deleteResult") == 0) {
204 xml_node result = current;
205 for (xml_node node = result.first_child(); node;
206 node = node.next_sibling()) {
207 ParseResultItem(node, add_change, list);
209 current = current.next_sibling();
211 current = current.first_child();
218 uint64_t sequence_number) {
220 pugi::xml_parse_result result = xdoc.load_buffer(data, length);
222 IFMAP_WARN(IFMapXmlLoadError,
"Unable to load XML document", length);
227 ParseResults(xdoc, &requests);
229 while (!requests.empty()) {
230 unique_ptr<DBRequest> req(requests.front());
231 requests.pop_front();
boost::function< bool(const pugi::xml_node &, std::unique_ptr< AutogenProperty > *) > MetadataParseFn
bool ParseMetadata(const pugi::xml_node &node, struct DBRequest *result) const
void MetadataRegister(const std::string &metadata, MetadataParseFn parser)
std::map< std::string, IFMapServerParser * > ModuleMap
std::unique_ptr< DBRequestData > data
bool Enqueue(DBRequest *req)
void SetOrigin(struct DBRequest *result) const
std::unique_ptr< AutogenProperty > content
void set_origin(Origin in_origin)
static ModuleMap module_map_
std::unique_ptr< DBRequestKey > key
static void IdentifierNsTypeName(const string &id, string *id_type, string *id_name)
void MetadataClear(const std::string &module)
bool Receive(DB *db, const char *data, size_t length, uint64_t sequence_number)
#define IFMAP_WARN(obj,...)
void ParseResults(const pugi::xml_document &xdoc, RequestList *list) const
std::list< struct DBRequest * > RequestList
static IFMapTable * FindTable(DB *db, const std::string &element_type)
static IFMapServerParser * GetInstance(const std::string &module)
static DBRequest * IFMapServerRequestClone(const DBRequest *src)
static string ParseIdentifier(const xml_node &node)
static const char * NodeName(const xml_node &node)
#define IFMAP_TRACE(obj,...)
bool ParseResultItem(const pugi::xml_node &parent, bool add_change, RequestList *list) const
static void DeleteInstance(const std::string &module)