Commit ddd461f1 authored by Abhishek Pandey's avatar Abhishek Pandey

EasySetup:Applied "href" and "rep" to POST request

IOT-2713: https://jira.iotivity.org/browse/IOT-2713

- Applied "href" and "rep" to POST request using oic.if.b (batch interface).
- Updated the handling for provision wifi & cloud properties
- Verified Enrollee & Mediator on Linux with sample apps.
- Linux Unit tests verified locally.
- Also fixed on build warning in easysetup_x.c (sample app).

Change-Id: I5e5d7c495d45dd8eb41ca5bcce2af8e18fd53c71
Signed-off-by: default avatarAbhishek Pandey <abhi.siso@samsung.com>
parent 5617a85d
......@@ -53,6 +53,7 @@ OCEntityHandlerResult ProcessGetRequest(OCEntityHandlerRequest *ehRequest, OCRep
OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload);
OCEntityHandlerResult ProcessPostRequest(OCEntityHandlerRequest *ehRequest, OCRepPayload** payload);
void updateEasySetupResource(OCEntityHandlerRequest* ehRequest, OCRepPayload* input);
void updateEasySetupConnectProperty(OCRepPayload* input);
void updateWiFiConfResource(OCRepPayload* input);
void updateCoapCloudConfResource(OCRepPayload* input);
void updateDevConfResource(OCRepPayload* input);
......@@ -341,6 +342,64 @@ void updateEasySetupResource(OCEntityHandlerRequest* ehRequest, OCRepPayload* in
{
OIC_LOG_V(DEBUG, ES_RH_TAG, "g_ESEasySetupResource.status %d", g_ESEasySetupResource.status);
// Below call is to allow cn update without 'rep' property.
// Can remove if no longer needed to support this way.
updateEasySetupConnectProperty(input);
if (ehRequest->query)
{
if (CompareResourceInterface(ehRequest->query, OC_RSRVD_INTERFACE_BATCH))
{
// When Provisioning resource has a POST with BatchInterface
// Parsing POST request on Batch Interface cosidering same format as GET using batch.
OCRepPayload *children = input;
while(children)
{
char* href = NULL;
OCRepPayloadGetPropString(children, OC_RSRVD_HREF, &href);
OIC_LOG_V(DEBUG, ES_RH_TAG, "href [%s]", href);
///TODO: Check why href value is null even though available in payload
OCRepPayload *repPayload = NULL;
OCRepPayloadGetPropObject(children, OC_RSRVD_REPRESENTATION, &repPayload);
char* uri = children->uri;
OIC_LOG_V(DEBUG, ES_RH_TAG, "uri [%s]", uri);
if(NULL == uri || NULL == repPayload)
{
children = children->next;
continue;
}
if (0 == strcmp(uri, OC_RSRVD_ES_URI_EASYSETUP))
{
updateEasySetupConnectProperty(repPayload);
}
else if (0 == strcmp(uri, OC_RSRVD_ES_URI_WIFICONF))
{
updateWiFiConfResource(repPayload);
}
else if (0 == strcmp(uri, OC_RSRVD_ES_URI_COAPCLOUDCONF))
{
updateCoapCloudConfResource(repPayload);
}
else if (0 == strcmp(uri, OC_RSRVD_ES_URI_DEVCONF))
{
updateDevConfResource(repPayload);
}
children = children->next;
OCRepPayloadDestroy(repPayload);
OICFree(href);
}
}
}
}
void updateEasySetupConnectProperty(OCRepPayload* input)
{
int64_t *connect_req = NULL;
size_t dimensions[MAX_REP_ARRAY_DEPTH] = { 0 };
if (OCRepPayloadGetIntArray(input, OC_RSRVD_ES_CONNECT, &connect_req, dimensions))
......@@ -386,17 +445,6 @@ void updateEasySetupResource(OCEntityHandlerRequest* ehRequest, OCRepPayload* in
}
}
}
if (ehRequest->query)
{
if (CompareResourceInterface(ehRequest->query, OC_RSRVD_INTERFACE_BATCH))
{
// When Provisioning resource has a POST with BatchInterface
updateCoapCloudConfResource(input);
updateWiFiConfResource(input);
updateDevConfResource(input);
}
}
}
void updateWiFiConfResource(OCRepPayload* input)
......@@ -1296,7 +1344,6 @@ OCStackResult CreateEasySetupResources(bool isSecured, ESResourceMask resourceMa
OIC_LOG_V(ERROR, ES_RH_TAG, "Bind WiFiConfResource result: %s", getResult(res));
return res;
}
}
if ((resourceMask & ES_COAPCLOUDCONF_RESOURCE) == ES_COAPCLOUDCONF_RESOURCE)
......@@ -1595,6 +1642,7 @@ OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest * ehRequest,
return ehResult;
}
/**
* This is the entity handler for the registered resource.
* This is invoked by OCStack whenever it recevies a request for this resource.
......
......@@ -45,6 +45,8 @@ using namespace OC;
using namespace std;
#define ES_RICH_COMMON_TAG "ES_MEDIATOR_COMMON"
#define OCF_CONTENT_FORMAT_VERSION_OPTION_ID 2053
#define OCF_CONTENT_FORMAT_VERSION_VALUE 2048
#ifndef WITH_ARDUINO
namespace OIC
......@@ -316,6 +318,57 @@ namespace OIC
{
return m_rep;
}
/**
* Update Cloud property representation as per OCF Specification.
*
* Resource Schema for CloudConf resource is different in older Enrollee following
* OIC Spec compared to newer Enrollee following OCF Spec. This function updates
* the representation as per spec version.
*/
void updateOCRepresentation(int specVersion)
{
if(0 == specVersion) // OIC Server does not contain CONTENT FORMAT VERSION
{
// Representation is already stored as per older resource schemas.
return;
}
// Representation should be updated as per OCF 1.3 Easy Setup resource schemas.
std::string authCode = m_rep.getValue<std::string>(OC_RSRVD_ES_AUTHCODE);
std::string authProvider = m_rep.getValue<std::string>(OC_RSRVD_ES_AUTHPROVIDER);
std::string ciServer = m_rep.getValue<std::string>(OC_RSRVD_ES_CISERVER);
std::string accessToken = m_rep.getValue<std::string>(OC_RSRVD_ES_ACCESSTOKEN);
OAUTH_TOKENTYPE accessTokenType = static_cast<OAUTH_TOKENTYPE>(
m_rep.getValue<int>(OC_RSRVD_ES_ACCESSTOKEN_TYPE));
OCRepresentation rootRep;
rootRep.setUri(OC_RSRVD_ES_URI_EASYSETUP);
OCRepresentation cloudDataRep;
if(authCode.length() > 0)
cloudDataRep.setValue(OC_RSRVD_ES_AUTHCODE, authCode);
if(accessToken.length() > 0)
{
cloudDataRep.setValue(OC_RSRVD_ES_ACCESSTOKEN, accessToken);
cloudDataRep.setValue(OC_RSRVD_ES_ACCESSTOKEN_TYPE, accessTokenType);
}
cloudDataRep.setValue(OC_RSRVD_ES_AUTHPROVIDER, authProvider);
cloudDataRep.setValue(OC_RSRVD_ES_CISERVER, ciServer);
OCRepresentation cloudconfRep;
cloudconfRep.setUri(OC_RSRVD_ES_URI_COAPCLOUDCONF);
cloudconfRep.setValue(OC_RSRVD_HREF, std::string(OC_RSRVD_ES_URI_COAPCLOUDCONF));
cloudconfRep.setValue(OC_RSRVD_REPRESENTATION, cloudDataRep);
rootRep.addChild(cloudconfRep);
m_rep = rootRep;
}
protected:
OCRepresentation m_rep;
std::string m_cloudID;
......@@ -448,13 +501,11 @@ namespace OIC
}
/**
* Get OCRepresentation object
* Update Device and Wi-Fi representation as per OCF Specification.
*
* Resource Schema for WiFiConf resource is different in older Enrollee following
* OIC Spec compared to newer Enrollee following OCF Spec. This function updates
* the representation as per spec version.
*
* Update representation as per OCF Specification.
*/
void updateOCRepresentation(int specVersion)
{
......@@ -468,8 +519,22 @@ namespace OIC
WIFI_AUTHTYPE authtype = static_cast<WIFI_AUTHTYPE> (m_rep.getValue<int>(OC_RSRVD_ES_AUTHTYPE));
WIFI_ENCTYPE enctype = static_cast<WIFI_ENCTYPE> (m_rep.getValue<int>(OC_RSRVD_ES_ENCTYPE));
m_rep.setValue(OC_RSRVD_ES_AUTHTYPE, getAuthTypeAsString(authtype));
m_rep.setValue(OC_RSRVD_ES_ENCTYPE, getEncTypeAsString(enctype));
OCRepresentation rootRep;
rootRep.setUri(OC_RSRVD_ES_URI_EASYSETUP);
OCRepresentation wifiDataRep;
wifiDataRep.setValue(OC_RSRVD_ES_SSID, m_rep.getValue<std::string>(OC_RSRVD_ES_SSID));
wifiDataRep.setValue(OC_RSRVD_ES_CRED, m_rep.getValue<std::string>(OC_RSRVD_ES_CRED));
wifiDataRep.setValue(OC_RSRVD_ES_AUTHTYPE, getAuthTypeAsString(authtype));
wifiDataRep.setValue(OC_RSRVD_ES_ENCTYPE, getEncTypeAsString(enctype));
OCRepresentation wificonfRep;
wificonfRep.setUri(OC_RSRVD_ES_URI_WIFICONF);
wificonfRep.setValue(OC_RSRVD_HREF, std::string(OC_RSRVD_ES_URI_WIFICONF));
wificonfRep.setValue(OC_RSRVD_REPRESENTATION, wifiDataRep);
rootRep.addChild(wificonfRep);
m_rep = rootRep;
}
protected:
......
......@@ -54,12 +54,59 @@ namespace OIC
}
}
int CloudResource::GetOCFServerVersion()
{
OIC_LOG (DEBUG, ES_CLOUD_RES_TAG, "GetOCFServerVersion IN");
HeaderOptions headerOptions = m_ocResource->getServerHeaderOptions();
if (headerOptions.size() == 0)
{
OIC_LOG (ERROR, ES_CLOUD_RES_TAG, "No header option exists");
}
else
{
for (auto it = headerOptions.begin(); it != headerOptions.end(); ++it)
{
if (it->getOptionID() == OCF_CONTENT_FORMAT_VERSION_OPTION_ID) // OPTION_CONTENT_VERSION
{
size_t dataLength = it->getOptionData().length();
if (dataLength == 0)
{
OIC_LOG (ERROR, ES_CLOUD_RES_TAG,
"GetOCFServerVersion: version value not found!");
// Content Format Version Header Option ID exist but not value.
// As OIC server don't use this header option ID, assuming as OCF Server.
return 1;
}
int version = (it->getOptionData().c_str()[0]) * 256;
OIC_LOG_V (INFO, ES_CLOUD_RES_TAG, "GetOCFServerVersion: Version [%d]", version);
if(OCF_CONTENT_FORMAT_VERSION_VALUE == version)
{
OIC_LOG_V (DEBUG, ES_CLOUD_RES_TAG,
"GetOCFServerVersion: Version matches OCF 1.0");
}
return version;
}
}
}
OIC_LOG (DEBUG, ES_CLOUD_RES_TAG, "GetOCFServerVersion OUT version option not found");
return 0;
}
void CloudResource::provisionProperties(const CloudProp& cloudProp)
{
OIC_LOG(DEBUG, ES_CLOUD_RES_TAG, "provisionProperties IN");
OCRepresentation provisioningRepresentation = cloudProp.toOCRepresentation();
int version = GetOCFServerVersion();
CloudProp cloudPropCopy = cloudProp;
cloudPropCopy.updateOCRepresentation(version);
OCRepresentation provisioningRepresentation = cloudPropCopy.toOCRepresentation();
ESCloudResourceCb cb = std::bind(&CloudResource::onCloudProvResponseSafetyCb,
std::placeholders::_1, std::placeholders::_2, std::placeholders::_3,
......
......@@ -63,6 +63,9 @@ namespace OIC
const OCRepresentation& rep,
const int eCode);
// Determine Specification Version Enrollee follows using header options from discovered resource
int GetOCFServerVersion();
private:
std::shared_ptr< OC::OCResource > m_ocResource;
CloudPropProvStatusCb m_cloudPropProvStatusCb;
......
......@@ -32,8 +32,6 @@ namespace OIC
namespace Service
{
#define ES_REMOTE_ENROLLEE_RES_TAG "ES_ENROLLEE_RESOURCE"
#define OCF_CONTENT_FORMAT_VERSION_OPTION_ID 2053
#define OCF_CONTENT_FORMAT_VERSION_VALUE 2048
EnrolleeResource::EnrolleeResource(std::shared_ptr< OC::OCResource > resource)
{
......
......@@ -622,7 +622,6 @@ namespace OIC
m_cloudEnrolleeSecurity = std::make_shared <EnrolleeSecurity> (m_ocResource);
}
res = m_cloudEnrolleeSecurity->provisionSecurityForCloudServer(cloudProp.getCloudID(),
cloudProp.getCredID());
......
......@@ -58,7 +58,7 @@ void ReadUserdataCb(OCRepPayload* payload, char* resourceType, void** userdata)
*userdata = (void*)OICMalloc(sizeof(UserProperties));
((UserProperties*)(*userdata))->userValue_int = value;
}
OIC_LOG_V(INFO, ESX_ENROLLEE_TAG, "[User specific property] %s : %ld",
OIC_LOG_V(INFO, ESX_ENROLLEE_TAG, "[User specific property] %s : %lld",
USERPROPERTY_KEY_INT, value);
g_userProperties.userValue_int = value;
}
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment