0
|
1 /* |
|
2 * command-watch.cpp -- implementation of irccdctl watch |
|
3 * |
|
4 * Copyright (c) 2013-2016 David Demelier <markand@malikania.fr> |
|
5 * |
|
6 * Permission to use, copy, modify, and/or distribute this software for any |
|
7 * purpose with or without fee is hereby granted, provided that the above |
|
8 * copyright notice and this permission notice appear in all copies. |
|
9 * |
|
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |
|
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |
|
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |
|
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |
|
14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN |
|
15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF |
|
16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |
|
17 */ |
|
18 |
|
19 #include <iostream> |
|
20 |
|
21 #include "command-watch.h" |
|
22 |
|
23 namespace irccd { |
|
24 |
|
25 namespace command { |
|
26 |
|
27 namespace { |
|
28 |
|
29 void onChannelMode(const json::Value &v) |
|
30 { |
|
31 std::cout << "event: onChannelMode\n"; |
|
32 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
33 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
34 std::cout << "mode: " << v.valueOr("mode", "").toString() << "\n"; |
|
35 std::cout << "argument: " << v.valueOr("argument", "").toString() << "\n"; |
|
36 } |
|
37 |
|
38 void onChannelNotice(const json::Value &v) |
|
39 { |
|
40 std::cout << "event: onChannelNotice\n"; |
|
41 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
42 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
43 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
44 std::cout << "notice: " << v.valueOr("notice", "").toString() << "\n"; |
|
45 } |
|
46 |
|
47 void onConnect(const json::Value &v) |
|
48 { |
|
49 std::cout << "event: onConnect\n"; |
|
50 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
51 } |
|
52 |
|
53 void onInvite(const json::Value &v) |
|
54 { |
|
55 std::cout << "event: onInvite\n"; |
|
56 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
57 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
58 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
59 } |
|
60 |
|
61 void onJoin(const json::Value &v) |
|
62 { |
|
63 std::cout << "event: onJoin\n"; |
|
64 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
65 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
66 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
67 } |
|
68 |
|
69 void onKick(const json::Value &v) |
|
70 { |
|
71 std::cout << "event: onKick\n"; |
|
72 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
73 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
74 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
75 std::cout << "target: " << v.valueOr("target", "").toString() << "\n"; |
|
76 std::cout << "reason: " << v.valueOr("reason", "").toString() << "\n"; |
|
77 } |
|
78 |
|
79 void onMessage(const json::Value &v) |
|
80 { |
|
81 std::cout << "event: onMessage\n"; |
|
82 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
83 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
84 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
85 std::cout << "message: " << v.valueOr("message", "").toString() << "\n"; |
|
86 } |
|
87 |
|
88 void onMe(const json::Value &v) |
|
89 { |
|
90 std::cout << "event: onMe\n"; |
|
91 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
92 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
93 std::cout << "target: " << v.valueOr("target", "").toString() << "\n"; |
|
94 std::cout << "message: " << v.valueOr("message", "").toString() << "\n"; |
|
95 } |
|
96 |
|
97 void onMode(const json::Value &v) |
|
98 { |
|
99 std::cout << "event: onMode\n"; |
|
100 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
101 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
102 std::cout << "mode: " << v.valueOr("mode", "").toString() << "\n"; |
|
103 } |
|
104 |
|
105 void onNames(const json::Value &v) |
|
106 { |
|
107 std::cout << "event: onNames\n"; |
|
108 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
109 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
110 std::cout << "names: " << v.valueOr("names", "").toJson(0) << "\n"; |
|
111 } |
|
112 |
|
113 void onNick(const json::Value &v) |
|
114 { |
|
115 std::cout << "event: onNick\n"; |
|
116 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
117 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
118 std::cout << "nickname: " << v.valueOr("nickname", "").toString() << "\n"; |
|
119 } |
|
120 |
|
121 void onNotice(const json::Value &v) |
|
122 { |
|
123 std::cout << "event: onNotice\n"; |
|
124 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
125 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
126 std::cout << "notice: " << v.valueOr("notice", "").toString() << "\n"; |
|
127 } |
|
128 |
|
129 void onPart(const json::Value &v) |
|
130 { |
|
131 std::cout << "event: onPart\n"; |
|
132 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
133 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
134 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
135 std::cout << "reason: " << v.valueOr("reason", "").toString() << "\n"; |
|
136 } |
|
137 |
|
138 void onQuery(const json::Value &v) |
|
139 { |
|
140 std::cout << "event: onQuery\n"; |
|
141 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
142 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
143 std::cout << "message: " << v.valueOr("message", "").toString() << "\n"; |
|
144 } |
|
145 |
|
146 void onTopic(const json::Value &v) |
|
147 { |
|
148 std::cout << "event: onTopic\n"; |
|
149 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
150 std::cout << "origin: " << v.valueOr("origin", "").toString() << "\n"; |
|
151 std::cout << "channel: " << v.valueOr("channel", "").toString() << "\n"; |
|
152 std::cout << "topic: " << v.valueOr("topic", "").toString() << "\n"; |
|
153 } |
|
154 |
|
155 void onWhois(const json::Value &v) |
|
156 { |
|
157 std::cout << "event: onWhois\n"; |
|
158 std::cout << "server: " << v.valueOr("server", "").toString() << "\n"; |
|
159 std::cout << "nickname: " << v.valueOr("nickname", "").toString() << "\n"; |
|
160 std::cout << "username: " << v.valueOr("username", "").toString() << "\n"; |
|
161 std::cout << "host: " << v.valueOr("host", "").toString() << "\n"; |
|
162 std::cout << "realname: " << v.valueOr("realname", "").toString() << "\n"; |
|
163 } |
|
164 |
|
165 const std::unordered_map<std::string, std::function<void (const json::Value &)>> events{ |
|
166 { "onChannelMode", onChannelMode }, |
|
167 { "onChannelNotice", onChannelNotice }, |
|
168 { "onConnect", onConnect }, |
|
169 { "onInvite", onInvite }, |
|
170 { "onJoin", onJoin }, |
|
171 { "onKick", onKick }, |
|
172 { "onMessage", onMessage }, |
|
173 { "onMe", onMe }, |
|
174 { "onMode", onMode }, |
|
175 { "onNames", onNames }, |
|
176 { "onNick", onNick }, |
|
177 { "onNotice", onNotice }, |
|
178 { "onPart", onPart }, |
|
179 { "onQuery", onQuery }, |
|
180 { "onTopic", onTopic }, |
|
181 { "onWhois", onWhois } |
|
182 }; |
|
183 |
|
184 } // !namespace |
|
185 |
|
186 void Watch::usage(Irccdctl &) const |
|
187 { |
|
188 log::warning() << "usage: " << sys::programName() << " watch [-f|--format native|json]\n\n"; |
|
189 log::warning() << "Start watching irccd events. You can use different output formats, native\n"; |
|
190 log::warning() << "is human readable format, json is pretty formatted json.\n\n"; |
|
191 log::warning() << "Example:\n"; |
|
192 log::warning() << "\t " << sys::programName() << " watch -f json" << std::endl; |
|
193 } |
|
194 |
|
195 void Watch::exec(Irccdctl &ctl, const std::vector<std::string> &args) const |
|
196 { |
|
197 std::vector<std::string> copy(args); |
|
198 std::string format("native"); |
|
199 |
|
200 parser::Options options{ |
|
201 { "-f", true }, |
|
202 { "--format", true } |
|
203 }; |
|
204 |
|
205 for (const auto &o : parser::read(copy, options)) |
|
206 if (o.first == "-f" || o.first == "--format") |
|
207 format = o.second; |
|
208 |
|
209 if (format != "native" && format != "json") |
|
210 throw std::invalid_argument("invalid format given: " + format); |
|
211 |
|
212 while (ctl.connection().isConnected()) { |
|
213 try { |
|
214 auto object = ctl.connection().next(-1); |
|
215 auto it = events.find(object.valueOr("event", "").toString()); |
|
216 |
|
217 /* Silently ignore to avoid breaking user output */ |
|
218 if (it == events.end()) |
|
219 continue; |
|
220 |
|
221 if (format == "json") { |
|
222 std::cout << object.toJson() << std::endl; |
|
223 } else { |
|
224 it->second(object); |
|
225 std::cout << std::endl; |
|
226 } |
|
227 } catch (...) { |
|
228 } |
|
229 } |
|
230 |
|
231 throw std::runtime_error("connection lost"); |
|
232 } |
|
233 |
|
234 } // !command |
|
235 |
|
236 } // !irccd |