hce-node application  1.4.3
HCE Hierarchical Cluster Engine node application
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
SphinxInputJsonMessageSearch.cpp
Go to the documentation of this file.
1 #include <Poco/JSON/Object.h>
2 #include <Poco/JSON/Array.h>
3 #include <Poco/JSON/JSON.h>
4 #include <Poco/JSON/Stringifier.h>
5 #include <Poco/JSON/Parser.h>
6 #include <Poco/JSON/JSONException.h>
7 
8 #include "EncodeDecodeBase64.hpp"
9 #include "SphinxError.hpp"
12 
13 namespace HCE
14 {
15 namespace sphinx
16 {
17 //-----------------------------------------------------------------------------
19 :inherited(), queryString(""),
20  queryParams(), orderParams(), filtersArray(), externalFields(), orderFields()
21 {
22  if (!json.empty())
23  unserialize(json);
24 }
25 //----------------------------------------------------------------------------
26 // cppcheck-suppress unusedFunction
27 void SphinxInputJsonMessageSearch::addQueryParameters(const std::string& paramName, const std::string& paramValue)
28 {
29  queryParams.push_back(std::make_pair(paramName, paramValue));
30 }
31 //-----------------------------------------------------------------------------
32 // cppcheck-suppress unusedFunction
33 void SphinxInputJsonMessageSearch::addOrderParameters(const std::string& paramName, const std::string& paramValue)
34 {
35  orderParams.push_back(std::make_pair(paramName, paramValue));
36 }
37 //-----------------------------------------------------------------------------
38 void SphinxInputJsonMessageSearch::addFilter(Poco::SharedPtr<SphinxFilter> pFilter)
39 {
40  filtersArray.addFilter(pFilter);
41 }
42 //-----------------------------------------------------------------------------
44  std::vector<std::string> attributeValues, SphinxFilter::ExcludeType exclude)
45 {
46  Poco::SharedPtr<SphinxFilter> pFilter(new SphinxFilter());
47  pFilter->setFilterType(filterType);
48  pFilter->setAttributeName(attributeName);
49  pFilter->setAttributeValues(attributeValues);
50  pFilter->setExcludeValue(exclude);
51  filtersArray.addFilter(pFilter);
52 }
53 //-----------------------------------------------------------------------------
54 // cppcheck-suppress unusedFunction
55 void SphinxInputJsonMessageSearch::addExternalFields(const std::string& fieldName)
56 {
57  externalFields.push_back(fieldName);
58 }
59 //-----------------------------------------------------------------------------
60 // cppcheck-suppress unusedFunction
61 void SphinxInputJsonMessageSearch::addOrderFields(const std::string& fieldName)
62 {
63  orderFields.push_back(fieldName);
64 }
65 //-----------------------------------------------------------------------------
66 std::string SphinxInputJsonMessageSearch::convertVarToString(Poco::Dynamic::Var& var) throw (std::exception)
67 {
68  std::string result;
69  if (var.isString())
70  result = var.convert<std::string>();
71  else if(var.isNumeric())
72  {
73  if(var.isInteger())
74  {
75  if(var.isSigned())
76  result = std::to_string(var.convert<long>());
77  else
78  result = std::to_string(var.convert<unsigned long>());
79  }
80  else
81  {
82  result = std::to_string(var.convert<double>());
83  }
84  }
85  return result;
86 }
87 //-----------------------------------------------------------------------------
89 {
90  _isError = false;
91  errorMsg.clear();
92  try
93  {
94  Poco::JSON::Object::Ptr obj = new Poco::JSON::Object();
96 
97  // serialize query parameters
98  Poco::JSON::Array::Ptr queryParameters = new Poco::JSON::Array();
99  obj->set(input_json_message_const::queryParameters, queryParameters);
100  Poco::JSON::Object::Ptr elem = new Poco::JSON::Object();
101  queryParameters->add(elem);
102  for (size_t i=0;i<queryParams.size();++i)
103  elem->set(queryParams[i].first, queryParams[i].second);
104  // add ext fields array to query parameters
105  Poco::JSON::Array::Ptr extArray = new Poco::JSON::Array();
107  for (size_t i=0;i<externalFields.size();++i)
108  extArray->add(externalFields[i]);
109 
110  // serialize order param
111  Poco::JSON::Array::Ptr orderParameters = new Poco::JSON::Array();
112  obj->set(input_json_message_const::orderParameters, orderParameters);
113  Poco::JSON::Object::Ptr elemOrder = new Poco::JSON::Object();
114  orderParameters->add(elemOrder);
115  for (size_t i=0;i<orderParams.size();++i)
116  elemOrder->set(orderParams[i].first, orderParams[i].second);
117  // add order ext fields to order param
118  Poco::JSON::Array::Ptr orderArray = new Poco::JSON::Array();
119  elemOrder->set(input_json_message_const::orderFieldsNames, orderArray);
120  for (size_t i=0;i<orderFields.size();++i)
121  orderArray->add(orderFields[i]);
122 
123  std::string filterString;
124  if (!filtersArray.serialize(filterString))
125  throw Poco::Exception(filtersArray.getErrorMsg());
127 
128  std::stringstream ostr;
129  Poco::JSON::Stringifier::stringify(obj, ostr);
130  json = ostr.str();
131  }
132  catch(std::exception& e)
133  {
134  errorMsg = e.what();
136  _isError = true;
137  }
138  return !_isError;
139 }
140 //-----------------------------------------------------------------------------
141 bool SphinxInputJsonMessageSearch::unserialize(const std::string& json)
142 {
143  queryString.clear();
144  queryParams.clear();
145  orderParams.clear();
146  filtersArray.clear();
147  externalFields.clear();
148  errorMsg.clear();
149  _isError = false;
150  try
151  {
152  Poco::JSON::Parser parser;
153  Poco::Dynamic::Var res = parser.parse(json);
154  Poco::JSON::Object::Ptr obj = res.extract<Poco::JSON::Object::Ptr>();
155 
156  Poco::Dynamic::Var tmp = obj->get(input_json_message_const::queryString);
157  if (tmp.isString())
158  queryString = decodeBase64(tmp.convert<std::string>());
159 
160  Poco::JSON::Array::Ptr queryParameters = obj->getArray(input_json_message_const::queryParameters);
161  if (queryParameters.isNull())
162  throw Poco::JSON::JSONException (std::string("array '").append(input_json_message_const::queryParameters).append("' not found"));
163 
164  for (size_t j = 0;j <queryParameters->size();++j)
165  {
166  tmp = queryParameters->get(j);
167  if (tmp.type() == typeid(Poco::JSON::Object::Ptr))
168  {
169  Poco::JSON::Object::Ptr elem = tmp.extract<Poco::JSON::Object::Ptr>();
170  std::vector<std::string> vecNames;
171  elem->getNames(vecNames);
172  for (size_t i=0;i<vecNames.size();++i)
173  {
174  tmp = elem->get(vecNames[i]);
175  if(tmp.isEmpty()) // check exists content
176  continue;
177 
179  {
180 
181  Poco::JSON::Array::Ptr extArray = elem->getArray(input_json_message_const::externalFieldsNames);
182  if (extArray.isNull())
183  throw Poco::JSON::JSONException (std::string("array '").append(input_json_message_const::externalFieldsNames).append("' not found"));
184 
185  for (size_t k=0;k<extArray->size();++k)
186  {
187  tmp = extArray->get(k);
188  if (tmp.isString())
189  externalFields.push_back(tmp.convert<std::string>());
190  }
191  }
192  else
193  queryParams.push_back(std::make_pair(vecNames[i], convertVarToString(tmp))); // analyze type and convert if input type Numeric or String
194  }
195  }
196  }
197 
198  Poco::JSON::Array::Ptr orderParameters = obj->getArray(input_json_message_const::orderParameters);
199  if (!orderParameters.isNull())
200  {
201  for (size_t j = 0;j <orderParameters->size();++j)
202  {
203  tmp = orderParameters->get(j);
204  if (tmp.type() == typeid(Poco::JSON::Object::Ptr))
205  {
206  Poco::JSON::Object::Ptr elem = tmp.extract<Poco::JSON::Object::Ptr>();
207  std::vector<std::string> vecNames;
208  elem->getNames(vecNames);
209  for (size_t i=0;i<vecNames.size();++i)
210  {
211  tmp = elem->get(vecNames[i]);
212  if(tmp.isEmpty()) // check exists content
213  continue;
214 
216  {
217 
218  Poco::JSON::Array::Ptr extArray = elem->getArray(input_json_message_const::orderFieldsNames);
219  if (extArray.isNull())
220  throw Poco::JSON::JSONException (std::string("array '").append(input_json_message_const::orderFieldsNames).append("' not found"));
221 
222  for (size_t k=0;k<extArray->size();++k)
223  {
224  tmp = extArray->get(k);
225  if (tmp.isString())
226  orderFields.push_back(tmp.convert<std::string>());
227  }
228  }
229  else
230  orderParams.push_back(std::make_pair(vecNames[i], convertVarToString(tmp))); // analyze type and convert if input type Numeric or String
231 
232  }
233  }
234  }
235  }
236 
238  if (tmp.isString())
239  {
240  std::string filterString = decodeBase64(tmp.convert<std::string>());
241  if (!filtersArray.unserialize(filterString))
242  throw Poco::Exception(filtersArray.getErrorMsg());
243  }
244 
245  }
246  catch(Poco::JSON::JSONException& e)
247  {
248  errorMsg = e.message();
250  _isError = true;
251  }
252  catch(std::exception& e)
253  {
254  errorMsg = e.what();
256  _isError = true;
257  }
258  return !_isError;
259 }
260 //-----------------------------------------------------------------------------
261 std::istream& operator>>(std::istream& is, SphinxInputJsonMessageSearch& messageSearch)
262 {
263  std::string json;
264  is.seekg(0, std::ios::end);
265  json.resize(is.tellg());
266  is.seekg(0, std::ios::beg);
267  is.read(const_cast<char*>(json.c_str()), json.size());
268  messageSearch.unserialize(json);
269  return is;
270 }
271 //-----------------------------------------------------------------------------
272 std::ostream& operator<<(std::ostream& os, const SphinxInputJsonMessageSearch& messageSearch)
273 {
274  std::string json;
275  const_cast<SphinxInputJsonMessageSearch&>(messageSearch).serialize(json);
276  return os << json;
277 }
278 //-----------------------------------------------------------------------------
279 //-----------------------------------------------------------------------------
280 } // end namespace sphinx
281 } // end namespace HCE