33 #include "rapidjson/writer.h"
34 #include "rapidjson/prettywriter.h"
35 #include "rapidjson/stringbuffer.h"
36 #include "rapidjson/filereadstream.h"
47 #include <BESSyntaxUserError.h>
50 #include <TheBESKeys.h>
55 #include "rjson_utils.h"
59 #define CMR_HOST_URL_KEY "CMR.host.url"
60 #define DEFAULT_CMR_HOST_URL "https://cmr.earthdata.nasa.gov/"
61 #define CMR_SEARCH_SERVICE "/search"
62 #define prolog string("CmrApi::").append(__func__).append("() - ")
66 CmrApi::CmrApi() : d_cmr_search_endpoint_url(DEFAULT_CMR_HOST_URL){
68 string cmr_search_endpoint_url;
71 d_cmr_search_endpoint_url = cmr_search_endpoint_url;
73 string search(CMR_SEARCH_SERVICE);
74 if (d_cmr_search_endpoint_url.length() >= search.length()) {
75 if (0 != d_cmr_search_endpoint_url.compare (d_cmr_search_endpoint_url.length() - search.length(), search.length(), search)){
79 BESDEBUG(MODULE, prolog <<
"Using CMR search endpoint: " << d_cmr_search_endpoint_url << endl);
89 itr = obj.FindMember(
"children");
90 bool result = itr != obj.MemberEnd();
91 string msg = prolog + (result?
"Located":
"FAILED to locate") +
" the value 'children' in the object.";
92 BESDEBUG(MODULE, msg << endl);
94 throw CmrError(msg,__FILE__,__LINE__);
98 result = children.IsArray();
99 msg = prolog +
"The value 'children' is" + (result?
"":
" NOT") +
" an array.";
100 BESDEBUG(MODULE, msg << endl);
102 throw CmrError(msg,__FILE__,__LINE__);
113 bool result = cmr_doc.IsObject();
114 string msg = prolog +
"Json document is" + (result?
"":
" NOT") +
" an object.";
115 BESDEBUG(MODULE, msg << endl);
117 throw CmrError(msg,__FILE__,__LINE__);
122 result = itr != cmr_doc.MemberEnd();
123 msg = prolog + (result?
"Located":
"FAILED to locate") +
" the value 'feed'.";
124 BESDEBUG(MODULE, msg << endl);
126 throw CmrError(msg,__FILE__,__LINE__);
130 result = feed.IsObject();
131 msg = prolog +
"The value 'feed' is" + (result?
"":
" NOT") +
" an object.";
132 BESDEBUG(MODULE, msg << endl);
134 throw CmrError(msg,__FILE__,__LINE__);
150 result = itr != feed.MemberEnd();
151 msg = prolog + (result?
"Located":
"FAILED to locate") +
" the value 'entry'.";
152 BESDEBUG(MODULE, msg << endl);
154 throw CmrError(msg,__FILE__,__LINE__);
158 result = entry.IsArray();
159 msg = prolog +
"The value 'entry' is" + (result?
"":
" NOT") +
" an Array.";
160 BESDEBUG(MODULE, msg << endl);
162 throw CmrError(msg,__FILE__,__LINE__);
180 result = itr != feed.MemberEnd();
181 msg = prolog + (result?
"Located":
"FAILED to locate") +
" the value 'facets'." ;
182 BESDEBUG(MODULE, msg << endl);
184 throw CmrError(msg,__FILE__,__LINE__);
188 result = facets_obj.IsObject();
189 msg = prolog +
"The value 'facets' is" + (result?
"":
" NOT") +
" an object.";
190 BESDEBUG(MODULE, msg << endl);
192 throw CmrError(msg,__FILE__,__LINE__);
199 string facet_title = ru.getStringValue(facet,
"title");
200 string temporal_title(
"Temporal");
201 if(facet_title == temporal_title){
202 msg = prolog +
"Found Temporal object.";
203 BESDEBUG(MODULE, msg << endl);
207 msg = prolog +
"The child of 'facets' with title '"+facet_title+
"' does not match 'Temporal'";
208 BESDEBUG(MODULE, msg << endl);
211 msg = prolog +
"Failed to locate the Temporal facet.";
212 BESDEBUG(MODULE, msg << endl);
213 throw CmrError(msg,__FILE__,__LINE__);
230 string temporal_child_title = rju.getStringValue(temporal_child,
"title");
231 string year_title(
"Year");
232 if(temporal_child_title == year_title){
233 msg = prolog +
"Found Year object.";
234 BESDEBUG(MODULE, msg << endl);
235 return temporal_child;
238 msg = prolog +
"The child of 'Temporal' with title '"+temporal_child_title+
"' does not match 'Year'";
239 BESDEBUG(MODULE, msg << endl);
242 msg = prolog +
"Failed to locate the Year group.";
243 BESDEBUG(MODULE, msg << endl);
244 throw CmrError(msg,__FILE__,__LINE__);
260 string year_title = rju.getStringValue(year_obj,
"title");
261 if(r_year == year_title){
262 msg = prolog +
"Found Year object.";
263 BESDEBUG(MODULE, msg << endl);
268 string title = rju.getStringValue(child,
"title");
269 string month_title(
"Month");
270 if(title == month_title){
271 msg = prolog +
"Found Month object.";
272 BESDEBUG(MODULE, msg << endl);
276 msg = prolog +
"The child of 'Year' with title '"+title+
"' does not match 'Month'";
277 BESDEBUG(MODULE, msg << endl);
282 msg = prolog +
"The child of 'Year' group with title '"+year_title+
"' does not match the requested year ("+r_year+
")";
283 BESDEBUG(MODULE, msg << endl);
286 msg = prolog +
"Failed to locate the Year group.";
287 BESDEBUG(MODULE, msg << endl);
288 throw CmrError(msg,__FILE__,__LINE__);
292 CmrApi::get_month(
const string r_month,
const string r_year,
const rapidjson::Document &cmr_doc){
300 string month_id = rju.getStringValue(month,
"title");
301 if(month_id == r_month){
303 msg << prolog <<
"Located requested month ("<<r_month <<
")";
304 BESDEBUG(MODULE, msg.str() << endl);
309 msg << prolog <<
"The month titled '"<<month_id <<
"' does not match the requested month ("<< r_month <<
")";
310 BESDEBUG(MODULE, msg.str() << endl);
314 msg << prolog <<
"Failed to locate request Year/Month.";
315 BESDEBUG(MODULE, msg.str() << endl);
316 throw CmrError(msg.str(),__FILE__,__LINE__);
320 CmrApi::get_day_group(
const string r_month,
const string r_year,
const rapidjson::Document &cmr_doc){
329 string title = rju.getStringValue(
object,
"title");
330 string day_group_title =
"Day";
331 if(title == day_group_title){
333 msg << prolog <<
"Located Day group for year: " << r_year <<
" month: "<< r_month;
334 BESDEBUG(MODULE, msg.str() << endl);
339 msg << prolog <<
"Failed to locate requested Day year: " << r_year <<
" month: "<< r_month;
340 BESDEBUG(MODULE, msg.str() << endl);
341 throw CmrError(msg.str(),__FILE__,__LINE__);
352 CmrApi::get_years(
string collection_name, vector<string> &years_result){
358 "?concept_id=" + collection_name +
"&include_facets=v2";
368 years_result.push_back(year);
382 CmrApi::get_months(
string collection_name,
string r_year, vector<string> &months_result){
388 +
"?concept_id="+collection_name
389 +
"&include_facets=v2"
390 +
"&temporal_facet[0][year]="+r_year;
394 BESDEBUG(MODULE, prolog <<
"Got JSON Document: "<< endl << rju.
jsonDocToString(doc) << endl);
398 if(years.Size() != 1){
400 msg << prolog <<
"We expected to get back one year (" << r_year <<
") but we got back " << years.Size();
401 BESDEBUG(MODULE, msg.str() << endl);
402 throw CmrError(msg.str(),__FILE__,__LINE__);
407 if(year_title != r_year){
409 msg << prolog <<
"The returned year (" << year_title <<
") does not match the requested year ("<< r_year <<
")";
410 BESDEBUG(MODULE, msg.str() << endl);
411 throw CmrError(msg.str(),__FILE__,__LINE__);
415 if(year_children.Size() != 1){
417 msg << prolog <<
"We expected to get back one child for the year (" << r_year <<
") but we got back " << years.Size();
418 BESDEBUG(MODULE, msg.str() << endl);
419 throw CmrError(msg.str(),__FILE__,__LINE__);
424 if(title !=
string(
"Month")){
426 msg << prolog <<
"We expected to get back a Month object, but we did not.";
427 BESDEBUG(MODULE, msg.str() << endl);
428 throw CmrError(msg.str(),__FILE__,__LINE__);
435 months_result.push_back(month_id);
445 CmrApi::get_days(
string collection_name,
string r_year,
string r_month, vector<string> &days_result){
450 +
"?concept_id="+collection_name
451 +
"&include_facets=v2"
452 +
"&temporal_facet[0][year]="+r_year
453 +
"&temporal_facet[0][month]="+r_month;
457 BESDEBUG(MODULE, prolog <<
"Got JSON Document: "<< endl << rju.
jsonDocToString(cmr_doc) << endl);
459 const rapidjson::Value& day_group = get_day_group(r_month, r_year, cmr_doc);
464 days_result.push_back(day_id);
474 CmrApi::get_granule_ids(
string collection_name,
string r_year,
string r_month,
string r_day, vector<string> &granules_ids){
479 granule_search(collection_name, r_year, r_month, r_day, cmr_doc);
485 granules_ids.push_back(day_id);
495 CmrApi::granule_count(
string collection_name,
string r_year,
string r_month,
string r_day){
498 granule_search(collection_name, r_year, r_month, r_day, cmr_doc);
500 return entries.Size();
508 CmrApi::granule_search(
string collection_name,
string r_year,
string r_month,
string r_day,
rapidjson::Document &result_doc){
512 +
"?concept_id="+collection_name
513 +
"&include_facets=v2"
517 url +=
"&temporal_facet[0][year]="+r_year;
520 url +=
"&temporal_facet[0][month]="+r_month;
523 url +=
"&temporal_facet[0][day]="+r_day;
525 BESDEBUG(MODULE, prolog <<
"CMR Granule Search Request Url: : " << url << endl);
526 rju.getJsonDoc(url,result_doc);
527 BESDEBUG(MODULE, prolog <<
"Got JSON Document: "<< endl << rju.jsonDocToString(result_doc) << endl);
536 CmrApi::get_granules(
string collection_name,
string r_year,
string r_month,
string r_day, vector<Granule *> &granules){
540 granule_search(collection_name, r_year, r_month, r_day, cmr_doc);
547 granules.push_back(g);
555 CmrApi::get_collection_ids(std::vector<std::string> &collection_ids){
557 string key = CMR_COLLECTIONS;
561 +
"' field has not been configured.", __FILE__, __LINE__);
569 cmr::Granule* CmrApi::get_granule(
string collection_name,
string r_year,
string r_month,
string r_day,
string granule_id)
571 vector<Granule *> granules;
574 get_granules(collection_name, r_year, r_month, r_day, granules);
575 for(
size_t i=0; i<granules.size() ;i++){
576 string id = granules[i]->getName();
577 BESDEBUG(MODULE, prolog <<
"Comparing granule id: " << granule_id <<
" to collection member id: " <<
id << endl);
578 if(
id == granule_id){
579 result = granules[i];
exception thrown if internal error encountered
static std::string pathConcat(const std::string &firstPart, const std::string &secondPart, char separator='/')
Concatenate path fragments making sure that they are separated by a single '/' character.
static std::string assemblePath(const std::string &firstPart, const std::string &secondPart, bool leadingSlash=false, bool trailingSlash=false)
Assemble path fragments making sure that they are separated by a single '/' character.
(Constant) member iterator for a JSON object value
void get_value(const std::string &s, std::string &val, bool &found)
Retrieve the value of a given key, if set.
static TheBESKeys * TheKeys()
void get_values(const std::string &s, std::vector< std::string > &vals, bool &found)
Retrieve the values of a given key, if set.
std::string jsonDocToString(rapidjson::Document &d)
void getJsonDoc(const std::string &url, rapidjson::Document &d)
std::string getStringValue(const rapidjson::Value &object, const std::string &name)
GenericValue< UTF8<> > Value
GenericValue with UTF8 encoding.
GenericDocument< UTF8<> > Document
GenericDocument with UTF8 encoding.
RAPIDJSON_NAMESPACE_BEGIN typedef unsigned SizeType
Size type (for string lengths, array sizes, etc.)