#include "simulator_resource_creator.h"
#include "simulator_logger.h"
#include <RamlParser.h>
-#include <boost/lexical_cast.hpp>
+#include "logger.h"
-using namespace RAML;
+#define TAG "SIM_RESOURCE_CREATOR"
unsigned int SimulatorResourceCreator::s_id;
SimulatorResourceServerImplSP SimulatorResourceCreator::createResource(
const std::string &configPath)
{
- RamlParser *ramlParser = new RamlParser(configPath);
- RamlPtr raml = ramlParser->getRamlPtr();
- for (auto resourceElement : raml->getResources())
+ RAML::RamlPtr raml;
+
+ try
+ {
+ RAML::RamlParser *ramlParser = new RAML::RamlParser(configPath);
+ raml = ramlParser->getRamlPtr();
+ }
+ catch (RAML::RamlException &e)
+ {
+ OC_LOG_V(ERROR, TAG, "RAML Exception occured! [%s]", e.what());
+ throw;
+ }
+
+ std::map<std::string, RAML::RamlResourcePtr> ramlResources = raml->getResources();
+ RAML::RamlResourcePtr ramlResource;
+ if (0 == ramlResources.size() || (ramlResource = ramlResources.begin()->second) == nullptr)
{
- SimulatorResourceServerImplSP resource(new SimulatorResourceServerImpl());
- resource->setName(resourceElement.first);
- resource->setURI(resourceElement.second->getResourceUri());
+ OC_LOG(ERROR, TAG, "Zero resources detected from RAML!");
+ return nullptr;
+ }
- // TODO: Currently setting only baseline interface.
- resource->setInterfaceType(OC::DEFAULT_INTERFACE);
- // TODO: Need to modify based on the spec for observable property
- resource->setObservable(true);
+ if (ramlResource)
+ {
+ SimulatorResourceServerImplSP simResource(new SimulatorResourceServerImpl());
+ simResource->setName(ramlResource->getDisplayName());
+ simResource->setURI(ramlResource->getResourceUri());
- for (auto action : resourceElement.second->getActions())
+ // Get the resource representation schema from GET response body
+ RAML::ActionPtr action = ramlResource->getAction(RAML::ActionType::GET);
+ if (!action)
{
- for (auto response : action.second->getResponses())
+ OC_LOG(ERROR, TAG, "Failed to create resource representation schema as it does not"
+ "posess the GET request!");
+ return nullptr;
+ }
+
+ RAML::ResponsePtr getResponse = action->getResponse("200");
+ if (!getResponse)
+ {
+ OC_LOG(ERROR, TAG, "Resource does not provide valid GET response!");
+ return nullptr;
+ }
+
+ RAML::RequestResponseBodyPtr responseBody = getResponse->getResponseBody("application/json");
+ if (responseBody)
+ {
+ RAML::JsonSchemaPtr resourceProperties = responseBody->getSchema()->getProperties();
+ for ( auto &propertyElement : resourceProperties->getProperties())
{
- for (auto bdy : response.second->getResponseBody())
+ if (!propertyElement.second)
+ continue;
+
+ std::string propName = propertyElement.second->getName();
+ if ("rt" == propName || "resourceType" == propName)
{
- auto resourceProperties = bdy.second->getSchema()->getProperties();
-
- for ( auto property : resourceProperties->getProperties() )
- {
- std::string propName = property.second->getName();
-
- if (propName == "rt")
- {
- resource->setResourceType(property.second->getValueString());
- continue;
- }
-
- // Include more property names if required based on spec support.
- if (propName == "if" || propName == "p" || propName == "n" || propName == "id")
- continue;
-
- SimulatorResourceModel::Attribute *attr = new SimulatorResourceModel::Attribute(propName);
-
- int type = property.second->getValueType();
- switch (type)
- {
- case 0: // Integer
- {
- int attributeValue = property.second->getValueInt();
- attr->setValue(attributeValue);
- }
- break;
-
- case 3: // String
- {
- std::string attributeValue = property.second->getValueString();
- attr->setValue(attributeValue);
- }
- break;
- }
-
- attr->setUpdateFrequencyTime(property.second->getUpdateFrequencyTime());
-
- int min = 0, max = 0, multipleof = 0;
- property.second->getRange(min, max, multipleof);
- attr->setRange(min, max);
-
- if (property.second->getAllowedValuesSize() > 0)
- attr->setAllowedValues(property.second->getAllowedValues());
-
- resource->addAttribute(*attr);
- }
-
- resource->setURI(constructURI(resource->getURI()));
- return resource;
+ simResource->setResourceType(propertyElement.second->getValueString());
+ continue;
}
+ else if ("if" == propName)
+ {
+ simResource->setInterfaceType(propertyElement.second->getValueString());
+ continue;
+ }
+ else if ("p" == propName || "n" == propName || "id" == propName)
+ {
+ continue;
+ }
+
+ // Build representation attribute
+ SimulatorResourceModel::Attribute attribute(propName);
+ switch (propertyElement.second->getValueType())
+ {
+ case 0: // Integer
+ attribute.setValue(propertyElement.second->getValue<int>());
+ break;
+
+ case 1: // Double
+ attribute.setValue(propertyElement.second->getValue<double>());
+ break;
+
+ case 2: // Boolean
+ attribute.setValue(propertyElement.second->getValue<bool>());
+ break;
+
+ case 3: // String
+ attribute.setValue(propertyElement.second->getValue<std::string>());
+ break;
+ }
+
+ // Set range/supported values set
+ int min = 0, max = 0, multipleof = 0;
+ propertyElement.second->getRange(min, max, multipleof);
+ attribute.setRange(min, max);
+
+ if (propertyElement.second->getAllowedValuesSize() > 0)
+ attribute.setAllowedValues(propertyElement.second->getAllowedValues());
+
+ simResource->addAttribute(attribute);
}
}
+
+ simResource->setURI(constructURI(simResource->getURI()));
+ return simResource;
}
return nullptr;