blob: a4bd21330a1c752d705fb402672fb0e0878ade58 [file] [log] [blame]
Paul Westbrookc18c7cf2015-10-27 06:38:59 -07001// 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
Johan Euphrosine3fb474e2015-10-29 15:23:53 -07005#include "examples/daemon/common/daemon.h"
6
Paul Westbrookc18c7cf2015-10-27 06:38:59 -07007#include <weave/device.h>
8#include <weave/enum_to_string.h>
9
10#include <base/bind.h>
11#include <base/memory/weak_ptr.h>
12
13namespace weave {
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070014namespace lockstate {
15enum class LockState { kUnlocked, kLocked, kPartiallyLocked };
16
17const weave::EnumToStringMap<LockState>::Map kLockMapMethod[] = {
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070018 {LockState::kLocked, "locked"},
19 {LockState::kUnlocked, "unlocked"},
20 {LockState::kPartiallyLocked, "partiallyLocked"}};
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070021} // namespace lockstate
22
23template <>
24EnumToStringMap<lockstate::LockState>::EnumToStringMap()
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070025 : EnumToStringMap(lockstate::kLockMapMethod) {}
26} // namespace weave
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070027
Alex Vakulenkod6db0492015-12-07 16:55:19 -080028namespace {
29
30const char kTraits[] = R"({
31 "lock": {
32 "commands": {
33 "setConfig": {
34 "minimalRole": "user",
35 "parameters": {
36 "lockedState": {
37 "type": "string",
38 "enum": [ "locked", "unlocked" ]
39 }
40 }
41 }
42 },
43 "state": {
44 "lockedState": {
45 "type": "string",
46 "enum": [ "locked", "unlocked", "partiallyLocked" ]
47 },
48 "isLockingSupported": { "type": "boolean" }
49 }
50 }
51})";
52
53const char kDefaultState[] = R"({
54 "lock":{"isLockingSupported": true}
55})";
56
57const char kComponent[] = "lock";
58
59} // anonymous namespace
60
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070061// LockHandler is a command handler example that shows
62// how to handle commands for a Weave lock.
63class LockHandler {
64 public:
65 LockHandler() = default;
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070066 void Register(weave::Device* device) {
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070067 device_ = device;
68
Alex Vakulenkod6db0492015-12-07 16:55:19 -080069 device->AddTraitDefinitionsFromJson(kTraits);
70 CHECK(device->AddComponent(kComponent, {"lock"}, nullptr));
71 CHECK(device->SetStatePropertiesFromJson(kComponent, kDefaultState,
72 nullptr));
73 UpdateLockState();
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070074
Alex Vakulenkod6db0492015-12-07 16:55:19 -080075 device->AddCommandHandler(kComponent, "lock.setConfig",
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070076 base::Bind(&LockHandler::OnLockSetConfig,
77 weak_ptr_factory_.GetWeakPtr()));
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070078 }
79
80 private:
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070081 void OnLockSetConfig(const std::weak_ptr<weave::Command>& command) {
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070082 auto cmd = command.lock();
83 if (!cmd)
84 return;
85 LOG(INFO) << "received command: " << cmd->GetName();
Vitaly Bukac4305602015-11-24 23:33:09 -080086 const auto& params = cmd->GetParameters();
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070087 std::string requested_state;
Vitaly Bukac4305602015-11-24 23:33:09 -080088 if (params.GetString("lockedState", &requested_state)) {
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070089 LOG(INFO) << cmd->GetName() << " state: " << requested_state;
90
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070091 weave::lockstate::LockState new_lock_status;
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070092
93 if (!weave::StringToEnum(requested_state, &new_lock_status)) {
94 // Invalid lock state was specified.
Johan Euphrosine3fb474e2015-10-29 15:23:53 -070095 weave::ErrorPtr error;
96 weave::Error::AddTo(&error, FROM_HERE, "example",
97 "invalid_parameter_value", "Invalid parameters");
Paul Westbrookc18c7cf2015-10-27 06:38:59 -070098 cmd->Abort(error.get(), nullptr);
99 return;
100 }
101
102 if (new_lock_status != lock_state_) {
103 lock_state_ = new_lock_status;
104
105 LOG(INFO) << "Lock is now: " << requested_state;
106 UpdateLockState();
107 }
108 cmd->Complete({}, nullptr);
109 return;
110 }
Johan Euphrosine3fb474e2015-10-29 15:23:53 -0700111 weave::ErrorPtr error;
112 weave::Error::AddTo(&error, FROM_HERE, "example", "invalid_parameter_value",
113 "Invalid parameters");
Paul Westbrookc18c7cf2015-10-27 06:38:59 -0700114 cmd->Abort(error.get(), nullptr);
115 }
116
Johan Euphrosine3fb474e2015-10-29 15:23:53 -0700117 void UpdateLockState() {
Paul Westbrookc18c7cf2015-10-27 06:38:59 -0700118 std::string updated_state = weave::EnumToString(lock_state_);
Alex Vakulenkod6db0492015-12-07 16:55:19 -0800119 device_->SetStateProperty(kComponent, "lock.lockedState",
120 base::StringValue{updated_state}, nullptr);
Paul Westbrookc18c7cf2015-10-27 06:38:59 -0700121 }
122
Johan Euphrosine3fb474e2015-10-29 15:23:53 -0700123 weave::Device* device_{nullptr};
Paul Westbrookc18c7cf2015-10-27 06:38:59 -0700124
125 // Simulate the state of the light.
Johan Euphrosine3fb474e2015-10-29 15:23:53 -0700126 weave::lockstate::LockState lock_state_{weave::lockstate::LockState::kLocked};
Paul Westbrookc18c7cf2015-10-27 06:38:59 -0700127 base::WeakPtrFactory<LockHandler> weak_ptr_factory_{this};
128};
129
Johan Euphrosine3fb474e2015-10-29 15:23:53 -0700130int main(int argc, char** argv) {
131 Daemon::Options opts;
132 if (!opts.Parse(argc, argv)) {
133 Daemon::Options::ShowUsage(argv[0]);
134 return 1;
135 }
136 Daemon daemon{opts};
137 LockHandler handler;
138 handler.Register(daemon.GetDevice());
139 daemon.Run();
140 return 0;
141}