Imported Upstream version 1.0.1
[platform/upstream/iotivity.git] / service / simulator / src / service-provider / resource_update_automation.cpp
1 /******************************************************************
2  *
3  * Copyright 2015 Samsung Electronics All Rights Reserved.
4  *
5  *
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  ******************************************************************/
20
21 #include "resource_update_automation.h"
22 #include "simulator_resource_server_impl.h"
23 #include "attribute_generator.h"
24 #include "simulator_exceptions.h"
25 #include "simulator_logger.h"
26 #include "logger.h"
27
28 #define ATAG "ATTRIBUTE_AUTOMATION"
29 #define RTAG "RESOURCE_AUTOMATION"
30
31 #define SLEEP_FOR(X) if (X > 0) std::this_thread::sleep_for(std::chrono::milliseconds(X));
32
33 AttributeUpdateAutomation::AttributeUpdateAutomation(int id, SimulatorResourceServer *resource,
34         const std::string &attrName, AutomationType type, int interval,
35         updateCompleteCallback callback, std::function<void (const int)> finishedCallback)
36     :   m_resource(resource),
37         m_attrName(attrName),
38         m_type(type),
39         m_id(id),
40         m_stopRequested(false),
41         m_updateInterval(interval),
42         m_callback(callback),
43         m_finishedCallback(finishedCallback),
44         m_thread(nullptr) {}
45
46 void AttributeUpdateAutomation::start()
47 {
48     // Check the validity of attribute
49     SimulatorResourceModel resModel = m_resource->getModel();
50     if (false == resModel.getAttribute(m_attrName, m_attribute))
51     {
52         OC_LOG_V(ERROR, ATAG, "Attribute:%s not present in resource!", m_attrName.c_str());
53         throw SimulatorException(SIMULATOR_ERROR, "Attribute is not present in resource!");
54     }
55
56     if (m_updateInterval < 0)
57     {
58         m_updateInterval = m_attribute.getUpdateFrequencyTime();
59         if (0 > m_updateInterval)
60             m_updateInterval = 0;
61     }
62
63     m_thread = new std::thread(&AttributeUpdateAutomation::updateAttribute, this);
64 }
65
66 void AttributeUpdateAutomation::stop()
67 {
68     m_stopRequested = true;
69     if (m_thread)
70         m_thread->join();
71 }
72
73 void AttributeUpdateAutomation::updateAttribute()
74 {
75     do
76     {
77         try
78         {
79             setAttributeValue();
80         }
81         catch (SimulatorException &e)
82         {
83             break;
84         }
85         if (m_stopRequested)
86             break;
87     }
88     while (AutomationType::RECURRENT == m_type);
89
90     if (!m_stopRequested)
91     {
92         OC_LOG_V(DEBUG, ATAG, "Attribute:%s automation is completed!", m_attrName.c_str());
93         SIM_LOG(ILogger::INFO, "Automation of " << m_attrName << " attribute is completed.");
94     }
95
96     // Notify application
97     if (m_callback)
98         m_callback(m_resource->getURI(), m_id);
99
100     if (m_finishedCallback && !m_stopRequested)
101         m_finishedCallback(m_id);
102 }
103
104 void AttributeUpdateAutomation::setAttributeValue()
105 {
106     SimulatorResourceServerImpl *resourceImpl =
107         dynamic_cast<SimulatorResourceServerImpl *>(m_resource);
108     if (!resourceImpl)
109         return;
110
111     if (SimulatorResourceModel::Attribute::ValueType::INTEGER ==
112             m_attribute.getValueType()) // For integer type values
113     {
114         int min;
115         int max;
116
117         m_attribute.getRange(min, max);
118         for (int value = min; value <= max; value++)
119         {
120             if (m_stopRequested)
121                 break;
122             resourceImpl->updateAttributeValue(m_attribute.getName(), value);
123             resourceImpl->notifyApp();
124             SLEEP_FOR(m_updateInterval);
125         }
126     }
127     else
128     {
129         for (int index = 0; index < m_attribute.getAllowedValuesSize(); index++)
130         {
131             if (m_stopRequested)
132                 break;
133             resourceImpl->updateFromAllowedValues(m_attribute.getName(), index);
134             resourceImpl->notifyApp();
135             SLEEP_FOR(m_updateInterval);
136         }
137     }
138 }
139
140 ResourceUpdateAutomation::ResourceUpdateAutomation(int id, SimulatorResourceServer *resource,
141         AutomationType type, int interval, updateCompleteCallback callback,
142         std::function<void (const int)> finishedCallback)
143     :   m_resource(resource),
144         m_type(type),
145         m_id(id),
146         m_stopRequested(false),
147         m_updateInterval(interval),
148         m_callback(callback),
149         m_finishedCallback(finishedCallback),
150         m_thread(nullptr) {}
151
152 void ResourceUpdateAutomation::start()
153 {
154     SimulatorResourceModel resModel = m_resource->getModel();
155     std::map<std::string, SimulatorResourceModel::Attribute> attributesTable =
156             resModel.getAttributes();
157     if (0 == attributesTable.size())
158     {
159         OC_LOG(ERROR, RTAG, "Resource has zero attributes!");
160         throw SimulatorException(SIMULATOR_ERROR, "Resource has zero attributes!");
161     }
162
163     std::vector<SimulatorResourceModel::Attribute> attributes;
164     for (auto &attributeEntry : attributesTable)
165         attributes.push_back(attributeEntry.second);
166
167     m_thread = new std::thread(&ResourceUpdateAutomation::updateAttributes, this, attributes);
168 }
169
170 void ResourceUpdateAutomation::stop()
171 {
172     m_stopRequested = true;
173     if (m_thread)
174         m_thread->join();
175 }
176
177 void ResourceUpdateAutomation::updateAttributes(
178         std::vector<SimulatorResourceModel::Attribute> attributes)
179 {
180     SimulatorResourceServerImpl *resourceImpl =
181         dynamic_cast<SimulatorResourceServerImpl *>(m_resource);
182
183     AttributeCombinationGen attrCombGen(attributes);
184     SimulatorResourceModel resModel;
185     while (!m_stopRequested && attrCombGen.next(resModel))
186     {
187         for (auto &attributeEntry : resModel.getAttributes())
188         {
189             resourceImpl->updateAttributeValue(attributeEntry.first, attributeEntry.second.getValue());
190         }
191
192         resourceImpl->notifyApp();
193         SLEEP_FOR(m_updateInterval);
194     }
195
196     // Notify application
197     if (m_callback)
198         m_callback(m_resource->getURI(), m_id);
199
200     if (m_finishedCallback && !m_stopRequested)
201         m_finishedCallback(m_id);
202 }
203