Newer
Older
* @copyright Copyright (c) 2022 University of Turku, MIT License
* @author Nicolas Pope
*/
#pragma once
#include <memory>
#include <string>
#include <vector>
#include <list>
#include <ftl/uuid.hpp>
#include <ftl/uri.hpp>
namespace ftl {
namespace net {
class Universe;
}
namespace protocol {
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
/**
* @brief A wrapper providing RPC API and local node management. Internally the
* Self instance is responsible for handling all network operations. Typically
* there is just a single instance of this class, but more can be created for
* testing purposes.
*
*/
class Self {
public:
/** Peer for outgoing connection: resolve address and connect */
explicit Self(const std::shared_ptr<ftl::net::Universe> &impl);
virtual ~Self();
/**
* @brief Connect to another host from this Self instance. Usually the
* namespace method can be used instead.
*
* @param uri A TCP URI.
* @return std::shared_ptr<ftl::protocol::Node>
*/
std::shared_ptr<ftl::protocol::Node> connectNode(const std::string &uri);
/**
* @brief Create a new stream. Use the namespace method if possible.
*
* @param uri A file:// or ftl:// URI.
* @return std::shared_ptr<ftl::protocol::Stream>
*/
std::shared_ptr<ftl::protocol::Stream> createStream(const std::string &uri);
/**
* @brief Open an existing stream. Use the namespace method if possible.
*
* @param uri A file:// or ftl:// URI
* @return std::shared_ptr<ftl::protocol::Stream>
*/
std::shared_ptr<ftl::protocol::Stream> getStream(const std::string &uri);
void start();
/**
* Open a new listening port on a given interfaces.
* eg. "tcp://localhost:9000"
* @param addr URI giving protocol, interface and port
*/
bool listen(const ftl::URI &addr);
/**
* @brief Get the list of all listening addresses and ports.
*
* @return std::vector<ftl::URI>
*/
std::vector<ftl::URI> getListeningURIs();
/**
* Essential to call this before destroying anything that registered
* callbacks or binds for RPC. It will terminate all connections and
* stop any network activity but without deleting the net object.
*/
void shutdown();
bool isConnected(const ftl::URI &uri);
bool isConnected(const std::string &s);
size_t numberOfNodes() const;
/**
* Will block until all currently registered connnections have completed.
* You should not use this, but rather use onConnect.
*/
int waitConnections(int seconds = 1);
/** get peer pointer by peer UUID, returns nullptr if not found */
std::shared_ptr<ftl::protocol::Node> getNode(const ftl::UUID &pid) const;
/** get webservice peer pointer, returns nullptr if not connected to webservice */
std::shared_ptr<ftl::protocol::Node> getWebService() const;
std::list<std::shared_ptr<ftl::protocol::Node>> getNodes() const;
/**
* @brief Register a callback for new node connections.
*
* @return ftl::Handle
*/
ftl::Handle onConnect(const std::function<bool(const std::shared_ptr<ftl::protocol::Node>&)>&);
/**
* @brief Register a callback for node disconnects.
*
* @return ftl::Handle
*/
ftl::Handle onDisconnect(const std::function<bool(const std::shared_ptr<ftl::protocol::Node>&)>&);
/**
* @brief Register a callback for any node or network errors. Note that the node pointer can
* be null if the error was not associated with a specific node.
*
* @return ftl::Handle
*/
ftl::Handle onError(
const std::function<bool(const std::shared_ptr<ftl::protocol::Node>&,
ftl::protocol::Error,
const std::string &)>&);
// Used for testing
ftl::net::Universe *getUniverse() const { return universe_.get(); }
protected:
std::shared_ptr<ftl::net::Universe> universe_;
} // namespace protocol
} // namespace ftl