1 // Copyright 2015 The Weave Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "src/commands/command_instance.h"
6 
7 #include <gtest/gtest.h>
8 #include <weave/test/unittest_utils.h>
9 
10 namespace weave {
11 
12 using test::CreateDictionaryValue;
13 using test::CreateValue;
14 
TEST(CommandInstanceTest,Test)15 TEST(CommandInstanceTest, Test) {
16   auto params = CreateDictionaryValue(R"({
17     'phrase': 'iPityDaFool',
18     'volume': 5
19   })");
20   CommandInstance instance{"robot.speak", Command::Origin::kCloud, *params};
21 
22   EXPECT_TRUE(
23       instance.Complete(*CreateDictionaryValue("{'foo': 239}"), nullptr));
24 
25   EXPECT_EQ("", instance.GetID());
26   EXPECT_EQ("robot.speak", instance.GetName());
27   EXPECT_EQ(Command::Origin::kCloud, instance.GetOrigin());
28   EXPECT_JSON_EQ("{'phrase': 'iPityDaFool', 'volume': 5}",
29                  instance.GetParameters());
30   EXPECT_JSON_EQ("{'foo': 239}", instance.GetResults());
31 
32   CommandInstance instance2{"base.reboot", Command::Origin::kLocal, {}};
33   EXPECT_EQ(Command::Origin::kLocal, instance2.GetOrigin());
34 }
35 
TEST(CommandInstanceTest,SetID)36 TEST(CommandInstanceTest, SetID) {
37   CommandInstance instance{"base.reboot", Command::Origin::kLocal, {}};
38   instance.SetID("command_id");
39   EXPECT_EQ("command_id", instance.GetID());
40 }
41 
TEST(CommandInstanceTest,FromJson)42 TEST(CommandInstanceTest, FromJson) {
43   auto json = CreateDictionaryValue(R"({
44     'name': 'robot.jump',
45     'component': 'comp1.comp2',
46     'id': 'abcd',
47     'parameters': {
48       'height': 53,
49       '_jumpType': '_withKick'
50     },
51     'results': {}
52   })");
53   std::string id;
54   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
55                                             &id, nullptr);
56   EXPECT_EQ("abcd", id);
57   EXPECT_EQ("abcd", instance->GetID());
58   EXPECT_EQ("robot.jump", instance->GetName());
59   EXPECT_EQ("comp1.comp2", instance->GetComponent());
60   EXPECT_JSON_EQ("{'height': 53, '_jumpType': '_withKick'}",
61                  instance->GetParameters());
62 }
63 
TEST(CommandInstanceTest,FromJson_ParamsOmitted)64 TEST(CommandInstanceTest, FromJson_ParamsOmitted) {
65   auto json = CreateDictionaryValue("{'name': 'base.reboot'}");
66   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
67                                             nullptr, nullptr);
68   EXPECT_EQ("base.reboot", instance->GetName());
69   EXPECT_JSON_EQ("{}", instance->GetParameters());
70 }
71 
TEST(CommandInstanceTest,FromJson_NotObject)72 TEST(CommandInstanceTest, FromJson_NotObject) {
73   auto json = CreateValue("'string'");
74   ErrorPtr error;
75   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
76                                             nullptr, &error);
77   EXPECT_EQ(nullptr, instance.get());
78   EXPECT_EQ("json_object_expected", error->GetCode());
79 }
80 
TEST(CommandInstanceTest,FromJson_NameMissing)81 TEST(CommandInstanceTest, FromJson_NameMissing) {
82   auto json = CreateDictionaryValue("{'param': 'value'}");
83   ErrorPtr error;
84   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
85                                             nullptr, &error);
86   EXPECT_EQ(nullptr, instance.get());
87   EXPECT_EQ("parameter_missing", error->GetCode());
88 }
89 
TEST(CommandInstanceTest,FromJson_ParamsNotObject)90 TEST(CommandInstanceTest, FromJson_ParamsNotObject) {
91   auto json = CreateDictionaryValue(R"({
92     'name': 'robot.speak',
93     'parameters': 'hello'
94   })");
95   ErrorPtr error;
96   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
97                                             nullptr, &error);
98   EXPECT_EQ(nullptr, instance.get());
99   auto inner = error->GetInnerError();
100   EXPECT_EQ("json_object_expected", inner->GetCode());
101   EXPECT_EQ("command_failed", error->GetCode());
102 }
103 
TEST(CommandInstanceTest,ToJson)104 TEST(CommandInstanceTest, ToJson) {
105   auto json = CreateDictionaryValue(R"({
106     'name': 'robot.jump',
107     'parameters': {
108       'height': 53,
109       '_jumpType': '_withKick'
110     },
111     'results': {}
112   })");
113   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
114                                             nullptr, nullptr);
115   EXPECT_TRUE(instance->SetProgress(*CreateDictionaryValue("{'progress': 15}"),
116                                     nullptr));
117   EXPECT_TRUE(instance->SetProgress(*CreateDictionaryValue("{'progress': 15}"),
118                                     nullptr));
119   instance->SetID("testId");
120   EXPECT_TRUE(instance->Complete(*CreateDictionaryValue("{'testResult': 17}"),
121                                  nullptr));
122 
123   json->MergeDictionary(CreateDictionaryValue(R"({
124     'id': 'testId',
125     'progress': {'progress': 15},
126     'state': 'done',
127     'results': {'testResult': 17}
128   })").get());
129 
130   auto converted = instance->ToJson();
131   EXPECT_PRED2([](const base::Value& val1,
132                   const base::Value& val2) { return val1.Equals(&val2); },
133                *json, *converted);
134 }
135 
TEST(CommandInstanceTest,ToJsonError)136 TEST(CommandInstanceTest, ToJsonError) {
137   auto json = CreateDictionaryValue(R"({
138     'name': 'base.reboot',
139     'parameters': {}
140   })");
141   auto instance = CommandInstance::FromJson(json.get(), Command::Origin::kCloud,
142                                             nullptr, nullptr);
143   instance->SetID("testId");
144 
145   ErrorPtr error;
146   Error::AddTo(&error, FROM_HERE, "CODE", "MESSAGE");
147   instance->Abort(error.get(), nullptr);
148 
149   json->MergeDictionary(CreateDictionaryValue(R"({
150     'id': 'testId',
151     'state': 'aborted',
152     'progress': {},
153     'results': {},
154     'error': {'code': 'CODE', 'message': 'MESSAGE'}
155   })").get());
156 
157   auto converted = instance->ToJson();
158   EXPECT_PRED2([](const base::Value& val1,
159                   const base::Value& val2) { return val1.Equals(&val2); },
160                *json, *converted);
161 }
162 
163 }  // namespace weave
164