add doxygen comments for exceptions in Scene-manager remote apis
[platform/upstream/iotivity.git] / service / scene-manager / src / RemoteSceneList.cpp
1 //******************************************************************
2 //
3 // Copyright 2016 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 "RemoteSceneList.h"
22
23 #include <map>
24 #include <algorithm>
25
26 #include "SceneCommons.h"
27 #include "RemoteSceneUtils.h"
28 #include "SceneListResourceRequestor.h"
29 #include "SceneCollectionResourceRequestor.h"
30 #include "OCPlatform.h"
31
32 namespace OIC
33 {
34     namespace Service
35     {
36
37         RemoteSceneList::RemoteSceneList(SceneListResourceRequestor::Ptr requestor)
38             : m_requestor{ requestor }
39         {
40
41         }
42
43         void RemoteSceneList::createInstance(RCSRemoteResourceObject::Ptr sceneListResource,
44                                              CreateInstanceCallback clientCB)
45         {
46             if (!clientCB)
47             {
48                 throw RCSInvalidParameterException{ "createInstance : Callback is NULL" };
49             }
50
51             if (sceneListResource == nullptr)
52             {
53                 throw RCSInvalidParameterException("Scene List resource object is null");
54             }
55
56             std::vector< std::string > rts = sceneListResource->getTypes();
57             auto it = std::find(rts.begin(), rts.end(), SCENE_LIST_RT);
58             if (it == rts.end())
59             {
60                 throw RCSInvalidParameterException(
61                     "Remote resource object is not a Scene List Resource");
62             }
63
64             SceneListResourceRequestor::Ptr pRequestor =
65                 std::make_shared< SceneListResourceRequestor >(sceneListResource);
66
67             std::string requestIf = SCENE_CLIENT_REQ_IF;
68             pRequestor->requestGet(requestIf, std::bind(
69                 &RemoteSceneList::onInstanceCreated,
70                 std::placeholders::_2, std::placeholders::_3, requestIf,
71                 pRequestor, std::move(clientCB)));
72         }
73
74         void RemoteSceneList::addNewSceneCollection(AddNewSceneCollectionCallback clientCB)
75         {
76             if (!clientCB)
77             {
78                 throw RCSInvalidParameterException{ "addNewSceneCollection : Callback is NULL" };
79             }
80
81             SceneListResourceRequestor::InternalCreateSceneCollectionCallback internalCB
82                 = std::bind(&RemoteSceneList::onSceneCollectionCreated, this,
83                 std::placeholders::_1, std::placeholders::_2, std::placeholders::_3,
84                 std::placeholders::_4, std::move(clientCB));
85
86             m_requestor->requestSceneCollectionCreation("", internalCB);
87         }
88
89         std::vector< RemoteSceneCollection::Ptr >
90             RemoteSceneList::getRemoteSceneCollections() const
91         {
92             std::lock_guard< std::mutex > collectionlock(m_collectionLock);
93             return m_remoteSceneCollections;
94         }
95
96         void RemoteSceneList::setName(const std::string &name, SetNameCallback clientCB)
97         {
98             if (!clientCB)
99             {
100                 throw RCSInvalidParameterException{ "setName : Callback is NULL" };
101             }
102
103             SceneListResourceRequestor::InternalSetNameCallback internalCB
104                 = std::bind(&RemoteSceneList::onNameSet, this,
105                 std::placeholders::_1, name, std::move(clientCB));
106
107             m_requestor->requestSetName(name, internalCB);
108         }
109
110         std::string RemoteSceneList::getName() const
111         {
112             std::lock_guard< std::mutex > lock(m_nameLock);
113             return m_name;
114         }
115
116         void RemoteSceneList::onInstanceCreated(
117             const RCSRepresentation &rep, int eCode, const std::string &If,
118             SceneListResourceRequestor::Ptr requestor, const CreateInstanceCallback &cb)
119         {
120             if (eCode == OC_STACK_OK)
121             {
122                 if (If == OC::DEFAULT_INTERFACE)
123                 {
124                     auto retPtr = buildSceneList(requestor, rep.getAttributes());
125                     cb(std::move(retPtr), SCENE_RESPONSE_SUCCESS);
126                 }
127                 else if (If == OC::BATCH_INTERFACE)
128                 {
129                     // TODO build remote scene list instance with batch interface.
130                 }
131                 else
132                 {
133                     // TODO error handle.
134                 }
135             }
136         }
137
138         RemoteSceneList::Ptr RemoteSceneList::buildSceneList(
139             SceneListResourceRequestor::Ptr requestor, const RCSResourceAttributes &attrs)
140         {
141             RemoteSceneList::Ptr newList(new RemoteSceneList(requestor));
142             auto collections = newList->parseSceneListFromAttributes(attrs);
143
144             try
145             {
146                 newList->m_name = attrs.at(SCENE_KEY_NAME).get< std::string >();
147
148                 for (const auto &itr : collections)
149                 {
150                     auto collection = itr.first;
151                     auto host = newList->getListResourceRequestor()
152                                     ->getRemoteResourceObject()->getAddress();
153
154                     RemoteSceneCollection::Ptr newCollection
155                         = newList->createRemoteSceneCollection(
156                                     host + collection.at(SCENE_KEY_URI).get< std::string >(),
157                                     collection.at(SCENE_KEY_ID).get< std::string >(),
158                                     collection.at(SCENE_KEY_NAME).get< std::string >());
159
160                     newCollection->addExistingRemoteScenes(
161                         collection.at(SCENE_KEY_SCENEVALUES).get< std::vector< std::string > >());
162
163                     newCollection->initializeRemoteScenes(itr.second, host);
164                 }
165             }
166             catch (const std::exception &e)
167             {
168                 SCENE_CLIENT_PRINT_LOG(e.what());
169             }
170
171             return std::move(newList);
172         }
173
174         RemoteSceneCollection::Ptr RemoteSceneList::createRemoteSceneCollection(
175             const std::string &link, const std::string &id, const std::string &name)
176         {
177             try
178             {
179                 std::vector< std::string > vecRT{ SCENE_COLLECTION_RT };
180                 std::vector< std::string > vecIF{ SCENE_CLIENT_REQ_IF };
181
182                 RCSRemoteResourceObject::Ptr pResource
183                     = SceneUtils::createRCSResourceObject(link, SCENE_CONNECTIVITY, vecRT, vecIF);
184
185                 SceneCollectionResourceRequestor::Ptr pRequestor(
186                     new SceneCollectionResourceRequestor(pResource));
187
188                 RemoteSceneCollection::Ptr newCollection(
189                     new RemoteSceneCollection(pRequestor, id, name));
190
191                 {
192                     std::lock_guard< std::mutex > collectionlock(m_collectionLock);
193                     m_remoteSceneCollections.push_back(newCollection);
194                 }
195
196                 return newCollection;
197             }
198             catch (const std::exception &e)
199             {
200                 SCENE_CLIENT_PRINT_LOG(e.what());
201                 return nullptr;
202             }
203         }
204
205         SceneListResourceRequestor::Ptr RemoteSceneList::getListResourceRequestor() const
206         {
207             return m_requestor;
208         }
209
210         std::vector<std::pair<RCSResourceAttributes, std::vector<RCSResourceAttributes>>>
211             RemoteSceneList::parseSceneListFromAttributes(const RCSResourceAttributes & listAttrs)
212         {
213             std::vector<std::pair<RCSResourceAttributes, std::vector<RCSResourceAttributes>>>
214                 retParsed;
215
216             auto collectionsResourceAttrs = getChildrenAttributes(listAttrs);
217
218             for (unsigned int i = 0; i < collectionsResourceAttrs.size(); ++i)
219             {
220                 retParsed.push_back(
221                     std::make_pair(
222                         collectionsResourceAttrs[i],
223                         getChildrenAttributes(collectionsResourceAttrs[i])));
224             }
225
226             return retParsed;
227         }
228
229         std::vector<RCSResourceAttributes> RemoteSceneList::getChildrenAttributes(
230             const RCSResourceAttributes & attrs) const
231         {
232             const std::string SCENE_CHILD = "child";
233
234             std::vector<RCSResourceAttributes> retChildren = {};
235
236             if (attrs.contains(SCENE_CHILD))
237             {
238                 retChildren
239                     = attrs.at(SCENE_CHILD).get<std::vector<RCSResourceAttributes>>();
240             }
241
242             return retChildren;
243         }
244
245         void RemoteSceneList::onSceneCollectionCreated(
246             const std::string &link, const std::string &id, const std::string &name, int eCode,
247             const AddNewSceneCollectionCallback &clientCB)
248         {
249             int result = SCENE_CLIENT_BADREQUEST;
250             RemoteSceneCollection::Ptr newCollection = nullptr;
251
252             if (eCode == SCENE_RESPONSE_SUCCESS)
253             {
254                 newCollection =
255                     createRemoteSceneCollection(link, id, name);
256
257                 if (newCollection)
258                     result = SCENE_RESPONSE_SUCCESS;
259             }
260
261             clientCB(newCollection, result);
262         }
263
264         void RemoteSceneList::onNameSet(int eCode, const std::string &name,
265             const SetNameCallback &clientCB)
266         {
267             int result = SCENE_CLIENT_BADREQUEST;
268             if (eCode == SCENE_RESPONSE_SUCCESS)
269             {
270                 std::lock_guard< std::mutex > lock(m_nameLock);
271                 m_name = name;
272                 result = SCENE_RESPONSE_SUCCESS;
273             }
274
275             clientCB(result);
276         }
277
278     }
279 }