eris 1.4.0
A WorldForge client library.
Response.cpp
1#include "Response.h"
2#include <Atlas/Objects/Operation.h>
3#include <memory>
4#include "LogStream.h"
5
6using namespace Atlas::Objects::Operation;
7
8namespace Eris
9{
10
11std::string getErrorMessage(const RootOperation & err)
12{
13 std::string msg;
14 const std::vector<Atlas::Objects::Root>& args = err->getArgs();
15 if (args.empty()) {
16 error() << "got Error error op from server without args";
17 msg = "Unknown error.";
18 } else {
19 const Atlas::Objects::Root & arg = args.front();
20 Atlas::Message::Element message;
21 if (arg->copyAttr("message", message) != 0) {
22 error() << "got Error error op from server without message";
23 msg = "Unknown error.";
24 } else {
25 if (!message.isString()) {
26 error() << "got Error error op from server with bad message";
27 msg = "Unknown error.";
28 } else {
29 msg = message.String();
30 }
31 }
32 }
33 return msg;
34}
35
36ResponseBase::~ResponseBase() = default;
37
38ResponseTracker::~ResponseTracker() = default;
39
40void ResponseTracker::await(std::int64_t serial, Callback callback)
41{
42 m_pending.emplace(serial, std::move(callback));
43}
44
45
46void ResponseTracker::await(std::int64_t serialno, std::unique_ptr<ResponseBase> resp)
47{
48 assert(m_pending.count(serialno) == 0);
49 std::shared_ptr<ResponseBase> holder = std::move(resp);
50 await(serialno, [holder](const Atlas::Objects::Operation::RootOperation& op)->Router::RouterResult{
51 auto result = holder->responseReceived(op);
52 return result ? Router::HANDLED : Router::IGNORED;
53 });
54}
55
56Router::RouterResult ResponseTracker::handleOp(const RootOperation& op)
57{
58 if (op->isDefaultRefno()) return Router::IGNORED; // invalid refno, not a response op
59
60 auto it = m_pending.find(op->getRefno());
61 if (it == m_pending.end()) {
62 warning() << "received op with valid refno (" << op->getRefno() <<
63 ") but no response is registered";
64 return Router::IGNORED;
65 }
66
67// order here is important, so the responseReceived can re-await the op
68 auto resp = it->second;
69 m_pending.erase(it);
70
71 auto result = resp(op);
72
73 return result;
74}
75
76Router::RouterResult NullResponse::responseReceived(const Atlas::Objects::Operation::RootOperation&)
77{
78 //debug() << "nullresponse, ignoring op with refno " << op->getRefno();
79 return Router::RouterResult::IGNORED;
80}
81
82void* clearMemberResponse(void* d)
83{
84 debug() << "clearing out member response object";
85
86 void** objectPointer = (void**) d;
87 *objectPointer = nullptr;
88 return nullptr;
89}
90
91} // of namespace
Router::RouterResult responseReceived(const Atlas::Objects::Operation::RootOperation &) override
Definition: Response.cpp:76
Definition: Account.cpp:33