/* **************************************************************************** * * mapGetIndividualContextEntityAttributes - */ HttpStatusCode mapGetIndividualContextEntityAttributes(const std::string& entityId, ContextElementResponse* response, ConnectionInfo* ciP) { HttpStatusCode ms; QueryContextRequest qcRequest; QueryContextResponse qcResponse; EntityId entity(entityId, "", "false"); // Here I fill in the 'query' entityId for the response response->contextElement.entityId.fill(entityId, "", "false"); qcRequest.entityIdVector.push_back(&entity); ms = mongoQueryContext(&qcRequest, &qcResponse, ciP->tenant, ciP->servicePathV, ciP->uriParam); if ((ms != SccOk) || (qcResponse.contextElementResponseVector.size() == 0)) { // Here I fill in statusCode for the response response->statusCode.fill(SccContextElementNotFound, std::string("Entity id: '") + entityId + "'"); LM_RE(ms, ("entityId '%s' not found", entityId.c_str())); } std::vector<ContextAttribute*> attrV = qcResponse.contextElementResponseVector.get(0)->contextElement.contextAttributeVector.vec; for (unsigned int ix = 0; ix < attrV.size() ; ++ix) { ContextAttribute* ca = new ContextAttribute(attrV[ix]); response->contextElement.contextAttributeVector.push_back(ca); } response->statusCode.fill(&qcResponse.contextElementResponseVector.get(0)->statusCode); return ms; }
/* **************************************************************************** * * postQueryContext - */ std::string postQueryContext(ConnectionInfo* ciP, int components, std::vector<std::string> compV, ParseData* parseDataP) { QueryContextResponse qcr; std::string answer; ciP->httpStatusCode = mongoQueryContext(&parseDataP->qcr.res, &qcr); answer = qcr.render(QueryContext, ciP->outFormat, ""); return answer; }
/* **************************************************************************** * * entityTypeWithoutFilter - * */ TEST(mongoQueryContextExistEntity, entityTypeWithoutFilter) { HttpStatusCode ms; QueryContextRequest req; QueryContextResponse res; utInit(); /* Prepare database */ prepareDatabase(); /* Forge the request (from "inside" to "outside") */ EntityId en("E1", "", "false"); req.entityIdVector.push_back(&en); /* Invoke the function in mongoBackend library */ ms = mongoQueryContext(&req, &res, "", servicePathVector , uriParams); /* Check response is as expected */ EXPECT_EQ(SccOk, ms); EXPECT_EQ(SccNone, res.errorCode.code); EXPECT_EQ("", res.errorCode.reasonPhrase); EXPECT_EQ("", res.errorCode.details); ASSERT_EQ(2, res.contextElementResponseVector.size()); /* Context Element response # 1 */ EXPECT_EQ("E1", RES_CER(0).entityId.id); EXPECT_EQ("T1", RES_CER(0).entityId.type); EXPECT_EQ("false", RES_CER(0).entityId.isPattern); ASSERT_EQ(1, RES_CER(0).contextAttributeVector.size()); EXPECT_EQ("A1", RES_CER_ATTR(0, 0)->name); EXPECT_EQ("TA1", RES_CER_ATTR(0, 0)->type); EXPECT_EQ("val1", RES_CER_ATTR(0, 0)->value); EXPECT_EQ(SccOk, RES_CER_STATUS(0).code); EXPECT_EQ("OK", RES_CER_STATUS(0).reasonPhrase); EXPECT_EQ(0, RES_CER_STATUS(0).details.size()); /* Context Element response # 2 */ EXPECT_EQ("E1", RES_CER(1).entityId.id); EXPECT_EQ("", RES_CER(1).entityId.type); EXPECT_EQ("false", RES_CER(1).entityId.isPattern); ASSERT_EQ(1, RES_CER(1).contextAttributeVector.size()); EXPECT_EQ("A1", RES_CER_ATTR(1, 0)->name); EXPECT_EQ("TA1", RES_CER_ATTR(1, 0)->type); EXPECT_EQ("val1b", RES_CER_ATTR(1, 0)->value); EXPECT_EQ(SccOk, RES_CER_STATUS(1).code); EXPECT_EQ("OK", RES_CER_STATUS(1).reasonPhrase); EXPECT_EQ(0, RES_CER_STATUS(1).details.size()); /* Release connection */ mongoDisconnect(); utExit(); }
/* **************************************************************************** * * mapGetIndividualContextEntity - */ HttpStatusCode mapGetIndividualContextEntity ( const std::string& entityId, const std::string& entityType, EntityTypeInfo typeInfo, ContextElementResponse* response, ConnectionInfo* ciP ) { HttpStatusCode ms; QueryContextRequest qcRequest; QueryContextResponse qcResponse; EntityId entity(entityId, entityType, "false"); // Here I fill in the 'query' entityId for the response response->contextElement.entityId.fill(entityId, entityType, "false"); qcRequest.entityIdVector.push_back(&entity); if ((typeInfo == EntityTypeEmpty) || (typeInfo == EntityTypeNotEmpty)) { Scope* scopeP = new Scope(SCOPE_FILTER_EXISTENCE, SCOPE_VALUE_ENTITY_TYPE); scopeP->oper = (typeInfo == EntityTypeEmpty)? SCOPE_OPERATOR_NOT : ""; qcRequest.restriction.scopeVector.push_back(scopeP); } ms = mongoQueryContext(&qcRequest, &qcResponse, ciP->tenant, ciP->servicePathV, ciP->uriParam); qcRequest.restriction.release(); if ((ms != SccOk) || (qcResponse.contextElementResponseVector.size() == 0)) { response->contextElement.entityId.fill(entityId, entityType, "false"); response->statusCode.fill(SccContextElementNotFound, std::string("Entity id: /") + entityId + "/"); LM_W(("Bad Input (entityId '%s' not found)", entityId.c_str())); return ms; } ContextElementResponse* cerP = qcResponse.contextElementResponseVector[0]; std::vector<ContextAttribute*> attrV = cerP->contextElement.contextAttributeVector.vec; response->contextElement.entityId.fill(&cerP->contextElement.entityId); for (unsigned int ix = 0; ix < attrV.size() ; ++ix) { ContextAttribute* ca = new ContextAttribute(attrV[ix]); response->contextElement.contextAttributeVector.push_back(ca); } response->contextElement.entityId.type = qcResponse.contextElementResponseVector.get(0)->contextElement.entityId.type; response->statusCode.fill(&qcResponse.contextElementResponseVector.get(0)->statusCode); return ms; }
/* **************************************************************************** * * entityTypeFilterNotExist - * */ TEST(mongoQueryContextExistEntity, entityTypeFilterNotExist) { HttpStatusCode ms; QueryContextRequest req; QueryContextResponse res; utInit(); /* Prepare database */ prepareDatabase(); /* Forge the request (from "inside" to "outside") */ EntityId en("E1", "", "false"); req.entityIdVector.push_back(&en); /* Define filter scope */ Scope sc; sc.type = SCOPE_FILTER_EXISTENCE; sc.oper = SCOPE_OPERATOR_NOT; sc.value = SCOPE_VALUE_ENTITY_TYPE; req.restriction.scopeVector.push_back(&sc); /* Invoke the function in mongoBackend library */ ms = mongoQueryContext(&req, &res, "", servicePathVector , uriParams); /* Check response is as expected */ EXPECT_EQ(SccOk, ms); EXPECT_EQ(SccNone, res.errorCode.code); EXPECT_EQ("", res.errorCode.reasonPhrase); EXPECT_EQ("", res.errorCode.details); ASSERT_EQ(1, res.contextElementResponseVector.size()); /* Context Element response # 1 */ EXPECT_EQ("E1", RES_CER(0).entityId.id); EXPECT_EQ("", RES_CER(0).entityId.type); EXPECT_EQ("false", RES_CER(0).entityId.isPattern); ASSERT_EQ(1, RES_CER(0).contextAttributeVector.size()); EXPECT_EQ("A1", RES_CER_ATTR(0, 0)->name); EXPECT_EQ("TA1", RES_CER_ATTR(0, 0)->type); EXPECT_EQ("val1b", RES_CER_ATTR(0, 0)->stringValue); EXPECT_EQ(SccOk, RES_CER_STATUS(0).code); EXPECT_EQ("OK", RES_CER_STATUS(0).reasonPhrase); EXPECT_EQ("", RES_CER_STATUS(0).details); utExit(); }
/* **************************************************************************** * * withoutType - * */ TEST(mongoQueryContextRequest_filters, withEntityType) { HttpStatusCode ms; QueryContextRequest req; QueryContextResponse res; /* Prepare database */ prepareDatabase(true); /* Forge the request (from "inside" to "outside") */ EntityId en(".*", "", "true"); Scope sc(SCOPE_TYPE_SIMPLE_QUERY, "+type"); req.entityIdVector.push_back(&en); req.restriction.scopeVector.push_back(&sc); /* Invoke the function in mongoBackend library */ servicePathVector.clear(); ms = mongoQueryContext(&req, &res, "", servicePathVector, uriParams); /* Check response is as expected */ EXPECT_EQ(SccOk, ms); EXPECT_EQ(SccNone, res.errorCode.code); EXPECT_EQ("", res.errorCode.reasonPhrase); EXPECT_EQ("", res.errorCode.details); /* Only entitie IDs are check (we have a bunch of tests in other places to check the query response itself */ ASSERT_EQ(9, res.contextElementResponseVector.size()); EXPECT_EQ("E1", RES_CER(0).entityId.id); EXPECT_EQ("E2", RES_CER(1).entityId.id); EXPECT_EQ("E3", RES_CER(2).entityId.id); EXPECT_EQ("E4", RES_CER(3).entityId.id); EXPECT_EQ("E5", RES_CER(4).entityId.id); EXPECT_EQ("C1", RES_CER(5).entityId.id); EXPECT_EQ("C2", RES_CER(6).entityId.id); EXPECT_EQ("C3", RES_CER(7).entityId.id); EXPECT_EQ("E6", RES_CER(8).entityId.id); /* Release dynamic memory used by response (mongoBackend allocates it) */ res.contextElementResponseVector.release(); /* Release connection */ setMongoConnectionForUnitTest(NULL); }
/* **************************************************************************** * * mapGetIndividualContextEntityAttribute - */ HttpStatusCode mapGetIndividualContextEntityAttribute ( const std::string& entityId, const std::string& entityType, const std::string& attributeName, ContextAttributeResponse* response, ConnectionInfo* ciP ) { HttpStatusCode ms; QueryContextRequest qcRequest; QueryContextResponse qcResponse; EntityId entity(entityId, entityType, "false"); qcRequest.entityIdVector.push_back(&entity); qcRequest.attributeList.push_back(attributeName); ms = mongoQueryContext(&qcRequest, &qcResponse, ciP->tenant, ciP->servicePathV, ciP->uriParam); if ((ms != SccOk) || (qcResponse.contextElementResponseVector.size() == 0)) { // Here I fill in statusCode for the response response->statusCode.fill(SccContextElementNotFound, std::string("Entity id: /") + entityId + "/"); LM_W(("Bad Input (entityId '%s' not found)", entityId.c_str())); return ms; } ContextElementResponse* cerP = qcResponse.contextElementResponseVector[0]; std::vector<ContextAttribute*> attrV = cerP->contextElement.contextAttributeVector.vec; for (unsigned int ix = 0; ix < attrV.size() ; ++ix) { ContextAttribute* ca = new ContextAttribute(attrV[ix]); response->contextAttributeVector.push_back(ca); } response->statusCode.fill(SccOk); return ms; }
/* **************************************************************************** * * getAttributeValueInstance - * * GET /ngsi10/contextEntities/{entityID}/attributes/{attributeName}/{valueID} */ std::string getAttributeValueInstance ( ConnectionInfo* ciP, int components, std::vector<std::string>& compV, ParseData* parseDataP ) { QueryContextRequest request; QueryContextResponse response; std::string entityId = compV[2]; std::string attributeName = compV[4]; std::string valueID = compV[5]; EntityId* eP = new EntityId(entityId, "", "false"); StatusCode sc; ContextAttributeResponse car; request.entityIdVector.push_back(eP); request.attributeList.push_back(attributeName); ciP->httpStatusCode = mongoQueryContext(&request, &response, ciP->tenant, ciP->servicePathV, ciP->uriParam); if (response.contextElementResponseVector.size() == 0) { car.statusCode.fill(SccContextElementNotFound, std::string("Entity-Attribute pair: /") + entityId + "-" + attributeName + "/"); } else { ContextElementResponse* cerP = response.contextElementResponseVector.get(0); ContextAttributeVector cav = cerP->contextElement.contextAttributeVector; // FIXME P4: as long as mongoQueryContext() signature is based on NGSI standard operations and that // standard queryContext doesn't allow specify metadata for attributes (note that it uses xs:string, // not full fledge attribute types), we cannot pass the ID to mongoBackend so we need to do the for loop // to grep the right attribute among all the ones returned by mongoQueryContext. However, this involves // a suboptimal query at mongoBackend, which could be improved passing it the ID as a new parameter to // mongoQueryContext() (although breaking the design principle about mongo*() functions follow the NGSI // standard). To think about it. for (unsigned int i = 0; i < cav.size(); i++) { if (cav.get(i)->getId() == valueID) { car.contextAttributeVector.push_back(cav.get(i)); } } if (cav.size() > 0 && car.contextAttributeVector.size() == 0) { car.statusCode.fill(SccContextElementNotFound, std::string("Attribute-ValueID pair: /") + attributeName + "-" + valueID + "/"); } else { car.statusCode.fill(&cerP->statusCode); } } request.release(); return car.render(ciP, AttributeValueInstance, ""); }