From ad427b9a7b27e2ae16fc8cb21d612794f4a71955 Mon Sep 17 00:00:00 2001 From: Determinant Date: Fri, 28 Jun 2019 19:19:57 -0400 Subject: add a minimal working example --- README.rst | 58 ++++++++++++++++++++++++++++++++++++++------------- test/.gitignore | 1 + test/CMakeLists.txt | 3 +++ test/test_p2p_min.cpp | 49 +++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 96 insertions(+), 15 deletions(-) create mode 100644 test/test_p2p_min.cpp diff --git a/README.rst b/README.rst index 54932bb..a9f8608 100644 --- a/README.rst +++ b/README.rst @@ -63,11 +63,41 @@ Dependencies - CMake >= 3.9 - C++14 - libuv -- libcrypto +- openssl >= 1.1.0 -Example (MsgNetwork layer) --------------------------- +Minimal working P2P network +--------------------------- +.. code-block:: cpp + + #include + #include "salticidae/event.h" + #include "salticidae/network.h" + + using Net = salticidae::PeerNetwork; + + int main() { /* exampmle of 4 peer nodes pinging each other */ + std::vector>> nodes; + Net::Config config; + salticidae::EventContext ec; + config.ping_period(2); + nodes.resize(4); + for (size_t i = 0; i < nodes.size(); i++) + { + salticidae::NetAddr addr("127.0.0.1:" + std::to_string(10000 + i)); + auto &net = (nodes[i] = std::make_pair(addr, std::make_unique(ec, config))).second; + net->start(); + net->listen(addr); + } + for (size_t i = 0; i < nodes.size(); i++) + for (size_t j = 0; j < nodes.size(); j++) + if (i != j) + nodes[i].second->add_peer(nodes[j].first); + ec.dispatch(); + return 0; + } +Using MsgNetwork class +---------------------- .. code-block:: cpp #include @@ -142,35 +172,33 @@ Example (MsgNetwork layer) { if (conn->get_mode() == ConnPool::Conn::ACTIVE) { - printf("[%s] Connected, sending hello.\n", + printf("[%s] connected, sending hello.\n", this->name.c_str()); /* send the first message through this connection */ send_msg(MsgHello(this->name, "Hello there!"), salticidae::static_pointer_cast(conn)); } else - printf("[%s] Accepted, waiting for greetings.\n", + printf("[%s] accepted, waiting for greetings.\n", this->name.c_str()); } else { - printf("[%s] Disconnected, retrying.\n", this->name.c_str()); + printf("[%s] disconnected, retrying.\n", this->name.c_str()); /* try to reconnect to the same address */ - connect(conn->get_addr()); + connect(conn->get_addr(), false); } + return true; }); } void on_receive_hello(MsgHello &&msg, const MyNet::conn_t &conn) { - printf("[%s] %s says %s\n", - name.c_str(), - msg.name.c_str(), msg.text.c_str()); + printf("[%s] %s says %s\n", name.c_str(), msg.name.c_str(), msg.text.c_str()); /* send acknowledgement */ send_msg(MsgAck(), conn); } }; - void on_receive_ack(MsgAck &&msg, const MyNet::conn_t &conn) { auto net = static_cast(conn->get_net()); printf("[%s] the peer knows\n", net->name.c_str()); @@ -182,8 +210,8 @@ Example (MsgNetwork layer) NetAddr bob_addr("127.0.0.1:12346"); /* test two nodes in the same main loop */ - MyNet alice(ec, "Alice", bob_addr); - MyNet bob(ec, "Bob", alice_addr); + MyNet alice(ec, "alice", bob_addr); + MyNet bob(ec, "bob", alice_addr); /* message handler could be a normal function */ alice.reg_handler(on_receive_ack); @@ -198,8 +226,8 @@ Example (MsgNetwork layer) bob.listen(bob_addr); /* try to connect once */ - alice.connect(bob_addr); - bob.connect(alice_addr); + alice.connect(bob_addr, false); + bob.connect(alice_addr, false); /* the main loop can be shutdown by ctrl-c or kill */ auto shutdown = [&](int) {ec.stop();}; diff --git a/test/.gitignore b/test/.gitignore index f50f029..50e25ba 100644 --- a/test/.gitignore +++ b/test/.gitignore @@ -4,6 +4,7 @@ test_msgnet test_p2p test_p2p_tls test_p2p_stress +test_p2p_min test_queue bench_network Makefile diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 0a1d3f1..15cd414 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -41,6 +41,9 @@ target_link_libraries(test_p2p_tls salticidae_static) add_executable(test_p2p_stress test_p2p_stress.cpp) target_link_libraries(test_p2p_stress salticidae_static) +add_executable(test_p2p_min test_p2p_min.cpp) +target_link_libraries(test_p2p_min salticidae_static) + add_executable(test_queue test_queue.cpp) target_link_libraries(test_queue salticidae_static pthread) diff --git a/test/test_p2p_min.cpp b/test/test_p2p_min.cpp new file mode 100644 index 0000000..a221d79 --- /dev/null +++ b/test/test_p2p_min.cpp @@ -0,0 +1,49 @@ +/** + * Copyright (c) 2019 Ava Labs, Inc. + * + * Author: Ted Yin + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of + * this software and associated documentation files (the "Software"), to deal in + * the Software without restriction, including without limitation the rights to + * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies + * of the Software, and to permit persons to whom the Software is furnished to do + * so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +#include +#include "salticidae/event.h" +#include "salticidae/network.h" + +using Net = salticidae::PeerNetwork; + +int main() { + std::vector>> nodes; + Net::Config config; + salticidae::EventContext ec; + config.ping_period(2); + nodes.resize(4); + for (size_t i = 0; i < nodes.size(); i++) + { + salticidae::NetAddr addr("127.0.0.1:" + std::to_string(10000 + i)); + auto &net = (nodes[i] = std::make_pair(addr, std::make_unique(ec, config))).second; + net->start(); + net->listen(addr); + } + for (size_t i = 0; i < nodes.size(); i++) + for (size_t j = 0; j < nodes.size(); j++) + if (i != j) + nodes[i].second->add_peer(nodes[j].first); + ec.dispatch(); + return 0; +} -- cgit v1.2.3