CYCLUS
infile_converters.cc
Go to the documentation of this file.
1 #include <sstream>
2 
3 #include <boost/shared_ptr.hpp>
4 #include <libxml++/libxml++.h>
5 
6 #include "error.h"
7 #include "infile_converters.h"
8 #include "infile_tree.h"
9 #include "pyhooks.h"
10 #include "pyne.h"
11 
12 namespace cyclus {
13 namespace toolkit {
14 
15 void AddJsonToXml(Json::Value& node, std::stringstream& ss,
16  std::string parent_name, std::string indent) {
17  using std::string;
18  using Json::Value;
19  if (node.isObject()) {
20  bool indent_child;
21  string name;
22  string newindent = indent + " ";
23  Value::Members members = node.getMemberNames();
24  for (int n = 0; n < members.size(); ++n) {
25  name = members[n];
26  if (node[name].isNull()) {
27  ss << indent << "<" << name << "/>\n";
28  continue;
29  }
30  indent_child = node[name].isObject();
31  if (!indent_child && node[name].isArray())
32  indent_child = node[name][0].isObject() || node[name][0].isArray();
33  ss << indent << "<" << name << ">";
34  if (indent_child)
35  ss << "\n";
36  AddJsonToXml(node[name], ss, name, newindent);
37  if (indent_child)
38  ss << indent;
39  ss << "</" << name << ">\n";
40  }
41  } else if (node.isArray()) {
42  bool indent_child;
43  std::string newindent = indent;
44  indent = indent.substr(0, indent.size() - 2);
45  int nchildren = node.size();
46  for (int n = 0; n < nchildren; ++n) {
47  if (node[n].isNull()) {
48  ss << indent << "<" << parent_name << "/>\n";
49  continue;
50  }
51  indent_child = node[n].isObject() || node[n].isArray();
52  if (n > 0) {
53  ss << indent << "<" << parent_name << ">";
54  if (indent_child)
55  ss << "\n";
56  }
57  AddJsonToXml(node[n], ss, parent_name, newindent);
58  if (n < nchildren - 1) {
59  if (indent_child)
60  ss << indent;
61  ss << "</" << parent_name << ">\n";
62  }
63  }
64  } else if (node.isString()) {
65  ss << node.asString();
66  } else if (node.isInt()) {
67  ss << node.asInt64();
68  } else if (node.isUInt()) {
69  ss << node.asUInt64();
70  } else if (node.isDouble()) {
71  ss << node.asDouble();
72  } else if (node.isBool()) {
73  ss << node.asBool();
74  } else {
75  // plain old data
76  ss << node.asString();
77  }
78 }
79 
80 // Converts a JSON string into an equivalent XML string
82  using std::string;
83  using std::stringstream;
84  using Json::Value;
85 
86  stringstream x;
87 
88  // parse the JSON string
89  Value root;
90  Json::Reader reader;
91  bool parsed = reader.parse(s, root, false);
92  if (!parsed) {
93  string msg = "Failed to parse JSON file into XML:\n" + \
94  reader.getFormattedErrorMessages();
95  throw ValidationError(msg);
96  }
97 
98  // convert to XML
99  AddJsonToXml(root, x, "", "");
100  return x.str();
101 }
102 
103 // inserts a value, or appends to an array
105  using std::string;
106  using Json::Value;
107  if (node.isMember(key)) {
108  if (node[key].isArray()) {
109  node[key].append(val);
110  } else {
111  Value keynode = node[key];
112  keynode = Value(Json::arrayValue);
113  keynode.append(node[key]);
114  keynode.append(val);
115  node[key] = keynode;
116  }
117  } else {
118  node[key] = val;
119  }
120 }
121 
122 void AddXmlToJson(InfileTree* xnode, Json::Value& jnode,
123  std::string parent_name) {
124  using std::string;
125  using Json::Value;
126  int n = xnode->NElements();
127  for (int i = 0; i < n; ++i) {
128  string name = xnode->GetElementName(i);
129  InfileTree* subxnode = xnode->SubTree("*", i);
130  Value val;
131  if (subxnode->NElements() == 0) {
132  try {
133  val = Value(subxnode->GetString("."));
134  } catch (cyclus::ValueError& e) {
135  val = Value(Json::nullValue);
136  }
137  } else {
138  val = Value(Json::objectValue);
139  AddXmlToJson(subxnode, val, name);
140  }
141  JsonInsertOrAppend(jnode, name, val);
142  }
143 }
144 
145 // Converts an XML string into an equivalent JSON string
147  using std::string;
148  using std::stringstream;
149  using Json::Value;
150  stringstream ss (s);
151  boost::shared_ptr<XMLParser> parser = boost::shared_ptr<XMLParser>(
152  new XMLParser());
153  parser->Init(ss);
154  InfileTree xroot(*parser);
155  Value jroot(Json::objectValue);
156  string rootname = parser->Document()->get_root_node()->get_name();
157  jroot[rootname] = Value(Json::objectValue);
158  AddXmlToJson(&xroot, jroot[rootname], rootname);
159  Json::CustomWriter writer = Json::CustomWriter("{", "}", "[", "]", ": ",
160  ", ", " ", 80);
161  return writer.write(jroot);
162 }
163 
165  return JsonToXml(PyToJson(s));
166 }
167 
169  return JsonToPy(XmlToJson(s));
170 }
171 
172 } // namespace toolkit
173 } // namespace cyclus
virtual int NElements()
Definition: infile_tree.cc:34
std::string PyToXml(std::string s)
Converts a Python string into an equivalent XML string.
std::string JsonToXml(std::string s)
Converts a JSON string into an equivalent XML string.
void AddJsonToXml(Json::Value &node, std::stringstream &ss, std::string parent_name, std::string indent)
std::string XmlToPy(std::string s)
Converts an XML string into an equivalent JSON string.
double asDouble() const
Definition: pyne.cc:15167
For values that are too big, too small, etc.
Definition: error.h:41
A class for extracting information from a given XML parser.
Definition: infile_tree.h:22
For validating files received via IO.
Definition: error.h:71
std::string name(int nuc)
Definition: pyne.cc:2940
bool parse(const std::string &document, Value &root, bool collectComments=true)
Read a Value from a JSON document.
Definition: pyne.cc:13250
std::string asString() const
Definition: pyne.cc:15006
Represents a JSON value.
Definition: pyne.h:3224
virtual std::string GetElementName(int index=0)
investigates the current status and returns a string representing the name of a given index ...
Definition: infile_tree.cc:93
bool asBool() const
Definition: pyne.cc:15221
A helper class to hold xml file data and provide automatic validation.
Definition: xml_parser.h:16
virtual std::string GetString(std::string query, int index=0)
investigates the current status and returns a string representing the content of a query at a given i...
Definition: infile_tree.cc:54
bool isMember(const char *key) const
Return true if the object has a member named key.
Definition: pyne.cc:15594
std::string JsonToPy(std::string infile)
Convert JSON string to Python simulation string.
Definition: pyhooks.cc:138
bool isDouble() const
Definition: pyne.cc:15695
std::string XmlToJson(std::string s)
Converts an XML string into an equivalent JSON string.
bool isInt() const
Definition: pyne.cc:15675
object value (collection of name/value pairs).
Definition: pyne.h:3145
Int64 asInt64() const
Definition: pyne.cc:15094
std::string PyToJson(std::string infile)
Convert Python simulation string to JSON.
Definition: pyhooks.cc:132
def indent(text, prefix, predicate=None)
bool isString() const
Definition: pyne.cc:15707
ArrayIndex size() const
Number of values in array or object.
Definition: pyne.cc:15295
void AddXmlToJson(InfileTree *xnode, Json::Value &jnode, std::string parent_name)
Writes a Value in JSON format with custom formatting.
Definition: pyne.h:4696
&#39;null&#39; value
Definition: pyne.h:3138
InfileTree * SubTree(std::string query, int index=0)
populates a child infile based on a query and index
Definition: infile_tree.cc:132
virtual std::string write(const Value &root)
Definition: pyne.cc:16888
taken directly from OsiSolverInterface.cpp on 2/17/14 from https://projects.coin-or.org/Osi/browser/trunk.
Definition: agent.cc:14
Unserialize a JSON document into a Value.
Definition: pyne.h:4246
bool isBool() const
Definition: pyne.cc:15669
UInt64 asUInt64() const
Definition: pyne.cc:15120
Members getMemberNames() const
Return a list of the member names.
Definition: pyne.cc:15614
bool isUInt() const
Definition: pyne.cc:15681
bool isArray() const
Definition: pyne.cc:15713
bool isObject() const
Definition: pyne.cc:15719
void JsonInsertOrAppend(Json::Value &node, std::string key, Json::Value &val)
Value & append(const Value &value)
Append value to array at the end.
Definition: pyne.cc:15536
array value (ordered list)
Definition: pyne.h:3144