tests: fix unit tests
Change-Id: I5740ebf6d17de1e9e4677f5a1773b54d0c1d6bec
diff --git a/tests/connectionManager.cpp b/tests/connectionManager.cpp
index 2a75f7b..60e6197 100644
--- a/tests/connectionManager.cpp
+++ b/tests/connectionManager.cpp
@@ -38,21 +38,22 @@
namespace dhtnet {
namespace test {
-struct ConnectionHandler {
+struct ConnectionHandler
+{
dht::crypto::Identity id;
std::shared_ptr<Logger> logger;
std::shared_ptr<tls::CertificateStore> certStore;
std::shared_ptr<dht::DhtRunner> dht;
std::shared_ptr<ConnectionManager> connectionManager;
std::shared_ptr<asio::io_context> ioContext;
- std::thread ioContextRunner;
+ std::shared_ptr<std::thread> ioContextRunner;
};
class ConnectionManagerTest : public CppUnit::TestFixture
{
public:
ConnectionManagerTest() {}
- ~ConnectionManagerTest() { }
+ ~ConnectionManagerTest() {}
static std::string name() { return "ConnectionManager"; }
void setUp();
void tearDown();
@@ -60,103 +61,92 @@
std::unique_ptr<ConnectionHandler> alice;
std::unique_ptr<ConnectionHandler> bob;
-//Create a lock to be used in the test units
+ // Create a lock to be used in the test units
std::mutex mtx;
std::shared_ptr<asio::io_context> ioContext;
- std::thread ioContextRunner;
+ std::shared_ptr<std::thread> ioContextRunner;
+ // std::thread ioContextRunner;
std::shared_ptr<Logger> logger;
std::unique_ptr<IceTransportFactory> factory;
-private:
+private:
std::unique_ptr<ConnectionHandler> setupHandler(const std::string& name);
- void testConnectDevice();
- // void testAcceptConnection();
- // void testMultipleChannels();
- // void testMultipleChannelsOneDeclined();
- // void testMultipleChannelsSameName();
- // void testDeclineConnection();
- // void testSendReceiveData();
- // void testAcceptsICERequest();
- // void testDeclineICERequest();
- // void testChannelRcvShutdown();
- // void testChannelSenderShutdown();
- // void testCloseConnectionWith();
- // void testShutdownCallbacks();
- // void testFloodSocket();
- // void testDestroyWhileSending();
- // void testIsConnecting();
- // void testCanSendBeacon();
- // void testCannotSendBeacon();
- // void testConnectivityChangeTriggerBeacon();
- // void testOnNoBeaconTriggersShutdown();
- // void testShutdownWhileNegotiating();
-
+ void testConnectDevice();
+ void testAcceptConnection();
+ void testMultipleChannels();
+ void testMultipleChannelsOneDeclined();
+ void testMultipleChannelsSameName();
+ void testDeclineConnection();
+ void testSendReceiveData();
+ void testAcceptsICERequest();
+ void testDeclineICERequest();
+ void testChannelRcvShutdown();
+ void testChannelSenderShutdown();
+ void testCloseConnectionWith();
+ void testShutdownCallbacks();
+ void testFloodSocket();
+ void testDestroyWhileSending();
+ void testIsConnecting();
+ void testCanSendBeacon();
+ void testCannotSendBeacon();
+ void testConnectivityChangeTriggerBeacon();
+ void testOnNoBeaconTriggersShutdown();
+ void testShutdownWhileNegotiating();
+ void testGetChannelList();
CPPUNIT_TEST_SUITE(ConnectionManagerTest);
-
- // CPPUNIT_TEST(testAcceptsICERequest);
- // CPPUNIT_TEST(testDeclineICERequest);
-
- CPPUNIT_TEST(testConnectDevice);
-
- // CPPUNIT_TEST(testIsConnecting);
-
- // CPPUNIT_TEST(testAcceptConnection);
- // CPPUNIT_TEST(testDeclineConnection);
-
- // CPPUNIT_TEST(testMultipleChannels);
- // CPPUNIT_TEST(testMultipleChannelsOneDeclined);
- // CPPUNIT_TEST(testMultipleChannelsSameName);
-
- // CPPUNIT_TEST(testSendReceiveData);
-
- // CPPUNIT_TEST(testChannelRcvShutdown);
- // CPPUNIT_TEST(testChannelSenderShutdown);
-
- // CPPUNIT_TEST(testCloseConnectionWith);
- // CPPUNIT_TEST(testShutdownCallbacks);
- // CPPUNIT_TEST(testFloodSocket);
- // CPPUNIT_TEST(testDestroyWhileSending);
-
- // CPPUNIT_TEST(testCanSendBeacon);
- // CPPUNIT_TEST(testCannotSendBeacon);
- // CPPUNIT_TEST(testConnectivityChangeTriggerBeacon);
- // CPPUNIT_TEST(testOnNoBeaconTriggersShutdown);
- // CPPUNIT_TEST(testShutdownWhileNegotiating);
+ CPPUNIT_TEST(testDeclineICERequest);
+ CPPUNIT_TEST(testConnectDevice);
+ CPPUNIT_TEST(testIsConnecting);
+ CPPUNIT_TEST(testAcceptConnection);
+ CPPUNIT_TEST(testDeclineConnection);
+ CPPUNIT_TEST(testMultipleChannels);
+ CPPUNIT_TEST(testMultipleChannelsOneDeclined);
+ CPPUNIT_TEST(testMultipleChannelsSameName);
+ CPPUNIT_TEST(testSendReceiveData);
+ CPPUNIT_TEST(testAcceptsICERequest);
+ CPPUNIT_TEST(testChannelRcvShutdown);
+ CPPUNIT_TEST(testChannelSenderShutdown);
+ CPPUNIT_TEST(testCloseConnectionWith);
+ CPPUNIT_TEST(testShutdownCallbacks);
+ CPPUNIT_TEST(testFloodSocket);
+ CPPUNIT_TEST(testDestroyWhileSending);
+ CPPUNIT_TEST(testCanSendBeacon);
+ CPPUNIT_TEST(testCannotSendBeacon);
+ CPPUNIT_TEST(testConnectivityChangeTriggerBeacon);
+ CPPUNIT_TEST(testOnNoBeaconTriggersShutdown);
+ CPPUNIT_TEST(testShutdownWhileNegotiating);
+ CPPUNIT_TEST(testGetChannelList);
CPPUNIT_TEST_SUITE_END();
};
CPPUNIT_TEST_SUITE_NAMED_REGISTRATION(ConnectionManagerTest, ConnectionManagerTest::name());
std::unique_ptr<ConnectionHandler>
-ConnectionManagerTest::setupHandler(const std::string& name) {
+ConnectionManagerTest::setupHandler(const std::string& name)
+{
auto h = std::make_unique<ConnectionHandler>();
auto ca = dht::crypto::generateIdentity("ca");
h->id = dht::crypto::generateIdentity(name, ca);
h->logger = logger;
h->certStore = std::make_shared<tls::CertificateStore>(name, h->logger);
h->ioContext = std::make_shared<asio::io_context>();
- h->ioContextRunner = std::thread([context = h->ioContext]() {
- try {
- auto work = asio::make_work_guard(*context);
- context->run();
- } catch (const std::exception& ex) {
- //print the error;
- }
- });
+ h->ioContext = ioContext;
+
+ h->ioContextRunner = ioContextRunner;
dht::DhtRunner::Config dhtConfig;
dhtConfig.dht_config.id = h->id;
dhtConfig.threaded = true;
dht::DhtRunner::Context dhtContext;
- dhtContext.certificateStore = [c=h->certStore](const dht::InfoHash& pk_id) {
+ dhtContext.certificateStore = [c = h->certStore](const dht::InfoHash& pk_id) {
std::vector<std::shared_ptr<dht::crypto::Certificate>> ret;
if (auto cert = c->getCertificate(pk_id.toString()))
ret.emplace_back(std::move(cert));
return ret;
};
- dhtContext.logger = h->logger;
+ // dhtContext.logger = h->logger;
h->dht = std::make_shared<dht::DhtRunner>();
h->dht->run(dhtConfig, std::move(dhtContext));
@@ -176,10 +166,7 @@
config->cachePath = tempDirPath.string();
h->connectionManager = std::make_shared<ConnectionManager>(config);
- h->connectionManager->onICERequest([](const DeviceId&) {
- return true;
- });
-
+ h->connectionManager->onICERequest([](const DeviceId&) { return true; });
return h;
}
@@ -193,78 +180,39 @@
logger->debug("Using OpenDHT version {}", dht::version());
ioContext = std::make_shared<asio::io_context>();
- ioContextRunner = std::thread([context = ioContext]() {
+ ioContextRunner = std::make_shared<std::thread>([context = ioContext]() {
try {
auto work = asio::make_work_guard(*context);
context->run();
} catch (const std::exception& ex) {
- //print the error;
+ // print the error;
}
});
+ // ioContextRunner = std::thread([context = ioContext]() {
+ // try {
+ // auto work = asio::make_work_guard(*context);
+ // context->run();
+ // } catch (const std::exception& ex) {
+ // // print the error;
+ // }
+ // });
factory = std::make_unique<IceTransportFactory>(logger);
alice = setupHandler("alice");
bob = setupHandler("bob");
}
-/*
- auto identifier = bobId.first->getPublicKey().getLongId();
- auto identifier = bobId.second->getLongId();
- auto identifier = bobId.second->getPublicKey().getLongId();
-*/
-
void
ConnectionManagerTest::tearDown()
{
- //wait_for_removal_of({aliceId, bobId}); //?????????????????????????????????
+ // wait_for_removal_of({aliceId, bobId});
+ // Stop the io_context and join the ioContextRunner thread
ioContext->stop();
- if (ioContextRunner.joinable())
- ioContextRunner.join();
+
+ if (ioContextRunner && ioContextRunner->joinable()) {
+ ioContextRunner->join();
+ }
}
-
-/*
-void
-ConnectionManagerTest::testConnectDevice()
-{
- auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
- auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-
- auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
- bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
- aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
- std::mutex mtx;
- std::unique_lock<std::mutex> lk {mtx};
- std::condition_variable cv, cvReceive;
- bool successfullyConnected = false;
- bool successfullyReceive = false;
-
- bobAccount->connectionManager().onChannelRequest(
- [&successfullyReceive, &cvReceive](const std::shared_ptr<dht::crypto::Certificate>&,
- const std::string& name) {
- successfullyReceive = name == "git://*";
- cvReceive.notify_one();
- return true;
- });
-
- aliceAccount->connectionManager().connectDevice(bobDeviceId,
- "git://*",
- [&](std::shared_ptr<ChannelSocket> socket,
- const DeviceId&) {
- if (socket) {
- successfullyConnected = true;
- }
- cv.notify_one();
- });
-
- CPPUNIT_ASSERT(cvReceive.wait_for(lk, 60s, [&] { return successfullyReceive; }));
- CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyConnected; }));
-
-
-}
-*/
-
void
ConnectionManagerTest::testConnectDevice()
{
@@ -275,1715 +223,1204 @@
alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
- bob->connectionManager->onChannelRequest([&isBobRecvChanlReq, &bobConVar]
- (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
- {
- isBobRecvChanlReq = name == "dumyName";
- bobConVar.notify_one();
- return true;
- });
+ bob->connectionManager->onChannelRequest(
+ [&isBobRecvChanlReq, &bobConVar](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ isBobRecvChanlReq = name == "dumyName";
+ bobConVar.notify_one();
+ return true;
+ });
std::condition_variable alicConVar;
bool isAlicConnected = false;
auto conctDevicCalBack = [&](std::shared_ptr<ChannelSocket> socket, const DeviceId&) {
- if (socket) { isAlicConnected = true; }
+ if (socket) {
+ isAlicConnected = true;
+ }
alicConVar.notify_one();
};
alice->connectionManager->connectDevice(bob->id.second, "dumyName", conctDevicCalBack);
- //Step 4: to check if Alice connected to Bob?
+ // Step 4: to check if Alice connected to Bob?
CPPUNIT_ASSERT(alicConVar.wait_for(lock, 60s, [&] { return isAlicConnected; }));
}
+void
+ConnectionManagerTest::testAcceptConnection()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
-// /*
-// void
-// ConnectionManagerTest::testAcceptConnection()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ successfullyReceive = name == "git://*";
+ return true;
+ });
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<ChannelSocket> socket) {
+ receiverConnected = socket && (name == "git://*");
+ });
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return successfullyReceive && successfullyConnected && receiverConnected;
+ }));
+}
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string& name) {
-// successfullyReceive = name == "git://*";
-// return true;
-// });
+void
+ConnectionManagerTest::testDeclineConnection()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string& name,
-// std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket && (name == "git://*");
-// });
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-// }
-// */
-// void
-// ConnectionManagerTest::testAcceptConnection()
-// {
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string&) {
+ successfullyReceive = true;
+ return false;
+ });
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string&,
+ std::shared_ptr<ChannelSocket> socket) {
+ if (socket)
+ receiverConnected = true;
+ });
-// auto chanlReqCalBack = [&successfullyReceive]
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
-// {
-// successfullyReceive = name == "dumyname";
-// return true;
-// };
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ cv.wait_for(lk, 30s);
+ CPPUNIT_ASSERT(successfullyReceive);
+ CPPUNIT_ASSERT(!successfullyConnected);
+ CPPUNIT_ASSERT(!receiverConnected);
+}
-// bobConMngr.onChannelRequest(chanlReqCalBack);
+void
+ConnectionManagerTest::testMultipleChannels()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyConnected2 = false;
+ int receiverConnected = 0;
-// bool receiverConnected = false;
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// auto conctReadyCalBack =[&receiverConnected]
-// (const DeviceId& deviceId, const std::string& name, std::shared_ptr<ChannelSocket> socket)
-// {
-// receiverConnected = socket && (name == "dumyname");
-// };
-
-// bobConMngr.onConnectionReady(conctReadyCalBack);
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string&,
+ std::shared_ptr<ChannelSocket> socket) {
+ if (socket)
+ receiverConnected += 1;
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected = true;
-// cv.notify_one();
-// };
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected2 = true;
+ }
+ cv.notify_one();
+ });
-// alicConMngr.connectDevice(bobDevicId, "dumyname", conctDevicCalBack);
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
+ }));
+ CPPUNIT_ASSERT(alice->connectionManager->activeSockets() == 1);
+}
+void
+ConnectionManagerTest::testMultipleChannelsOneDeclined()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyNotConnected = false;
+ bool successfullyConnected2 = false;
+ int receiverConnected = 0;
-// }
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name) {
+ if (name == "git://*")
+ return false;
+ return true;
+ });
-// /*
-// void
-// ConnectionManagerTest::testDeclineConnection()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket)
+ receiverConnected += 1;
+ cv.notify_one();
+ });
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (!socket)
+ successfullyNotConnected = true;
+ cv.notify_one();
+ });
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket)
+ successfullyConnected2 = true;
+ cv.notify_one();
+ });
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string&) {
-// successfullyReceive = true;
-// return false;
-// });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return successfullyNotConnected && successfullyConnected2 && receiverConnected == 1;
+ }));
+ CPPUNIT_ASSERT(alice->connectionManager->activeSockets() == 1);
+}
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string&,
-// std::shared_ptr<ChannelSocket> socket) {
-// if (socket)
-// receiverConnected = true;
-// });
+void
+ConnectionManagerTest::testMultipleChannelsSameName()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// cv.wait_for(lk, 30s);
-// CPPUNIT_ASSERT(successfullyReceive);
-// CPPUNIT_ASSERT(!successfullyConnected);
-// CPPUNIT_ASSERT(!receiverConnected);
-// }
-// */
-// void
-// ConnectionManagerTest::testDeclineConnection()
-// {
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyConnected2 = false;
+ int receiverConnected = 0;
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// auto chanlReqCalBack = [&successfullyReceive]
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string&)
-// {
-// successfullyReceive = true;
-// return false; //this is the point??????????????????????????????????????????????????????
-// };
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string&,
+ std::shared_ptr<ChannelSocket> socket) {
+ if (socket)
+ receiverConnected += 1;
+ });
-// bobConMngr.onChannelRequest(chanlReqCalBack);
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // We can open two sockets with the same name, it will be two different channel
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected2 = true;
+ }
+ cv.notify_one();
+ });
-// auto conctReadyCalBack =[&receiverConnected]
-// (const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket)
-// receiverConnected = true;
-// };
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
+ }));
+}
-// bobConMngr.onConnectionReady(conctReadyCalBack);
+void
+ConnectionManagerTest::testSendReceiveData()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected = true;
-// cv.notify_one();
-// };
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ std::atomic_int events(0);
+ bool successfullyConnected = false, successfullyConnected2 = false, successfullyReceive = false,
+ receiverConnected = false;
+ const uint8_t buf_other[] = {0x64, 0x65, 0x66, 0x67};
+ const uint8_t buf_test[] = {0x68, 0x69, 0x70, 0x71};
+ bool dataOk = false, dataOk2 = false;
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string&) {
+ successfullyReceive = true;
+ return true;
+ });
-// alicConMngr.connectDevice(bobDevicId, "dumyname", conctDevicCalBack);
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && (name == "test" || name == "other")) {
+ receiverConnected = true;
+ std::error_code ec;
+ auto res = socket->waitForData(std::chrono::milliseconds(5000), ec);
+ if (res == 4) {
+ uint8_t buf[4];
+ socket->read(&buf[0], 4, ec);
+ if (name == "test")
+ dataOk = std::equal(std::begin(buf), std::end(buf), std::begin(buf_test));
+ else
+ dataOk2 = std::equal(std::begin(buf), std::end(buf), std::begin(buf_other));
+ events++;
+ cv.notify_one();
+ }
+ }
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "test",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ std::error_code ec;
+ socket->write(&buf_test[0], 4, ec);
+ }
+ events++;
+ cv.notify_one();
+ });
-// cv.wait_for(lk, 30s);
-// CPPUNIT_ASSERT(successfullyReceive);
-// CPPUNIT_ASSERT(!successfullyConnected);
-// CPPUNIT_ASSERT(!receiverConnected);
-// }
+ alice->connectionManager->connectDevice(bob->id.second,
+ "other",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected2 = true;
+ std::error_code ec;
+ socket->write(&buf_other[0], 4, ec);
+ }
+ events++;
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return events == 4 && successfullyReceive && successfullyConnected && successfullyConnected2
+ && dataOk && dataOk2;
+ }));
+}
+void
+ConnectionManagerTest::testAcceptsICERequest()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// /*
-// void
-// ConnectionManagerTest::testMultipleChannels()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onICERequest([&](const DeviceId&) {
+ successfullyReceive = true;
+ return true;
+ });
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<ChannelSocket> socket) {
+ receiverConnected = socket && (name == "git://*");
+ });
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string&,
-// std::shared_ptr<ChannelSocket> socket) {
-// if (socket)
-// receiverConnected += 1;
-// });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
+ return successfullyReceive && successfullyConnected && receiverConnected;
+ }));
+}
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
+void
+ConnectionManagerTest::testDeclineICERequest()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected2 = true;
-// }
-// cv.notify_one();
-// });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
-// }));
-// CPPUNIT_ASSERT(aliceAccount->connectionManager().activeSockets() == 1);
-// }
-// */
-// void
-// ConnectionManagerTest::testMultipleChannels()
-// {
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
-// auto chanlReqCalBack = []
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string&)
-// {
-// return true;
-// };
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onICERequest([&](const DeviceId&) {
+ successfullyReceive = true;
+ return false;
+ });
-// bobConMngr.onChannelRequest(chanlReqCalBack);
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<ChannelSocket> socket) {
+ receiverConnected = socket && (name == "git://*");
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
-// auto conctReadyCalBack =[&receiverConnected]
-// (const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket)
-// receiverConnected += 1;
-// };
+ cv.wait_for(lk, 30s);
+ CPPUNIT_ASSERT(successfullyReceive);
+ CPPUNIT_ASSERT(!receiverConnected);
+ CPPUNIT_ASSERT(!successfullyConnected);
+}
-// bobConMngr.onConnectionReady(conctReadyCalBack);
+void
+ConnectionManagerTest::testChannelRcvShutdown()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected = true;
-// cv.notify_one();
-// };
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool shutdownReceived = false;
-// alicConMngr.connectDevice(bobDevicId, "git://*", conctDevicCalBack);
+ std::shared_ptr<ChannelSocket> bobSock;
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected2 = true;
-// cv.notify_one();
-// };
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId& did, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && name == "git://*" && did != bob->id.second->getLongId()) {
+ bobSock = socket;
+ cv.notify_one();
+ }
+ });
-// alicConMngr.connectDevice(bobDevicId, "sip://*", conctDevicCalBack);
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ socket->onShutdown([&] {
+ shutdownReceived = true;
+ cv.notify_one();
+ });
+ successfullyConnected = true;
+ cv.notify_one();
+ }
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return bobSock && successfullyConnected; }));
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
-// }));
-// CPPUNIT_ASSERT(alicConMngr.activeSockets() == 1);
-// }
+ bobSock->shutdown();
-// /*void
-// ConnectionManagerTest::testMultipleChannelsOneDeclined()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return shutdownReceived; }));
+}
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+void
+ConnectionManagerTest::testChannelSenderShutdown()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyNotConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name) {
-// if (name == "git://*")
-// return false;
-// return true;
-// });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable rcv, scv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
+ bool shutdownReceived = false;
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
-// if (socket)
-// receiverConnected += 1;
-// cv.notify_one();
-// });
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ successfullyReceive = name == "git://*";
+ return true;
+ });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (!socket)
-// successfullyNotConnected = true;
-// cv.notify_one();
-// });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
+ if (socket) {
+ socket->onShutdown([&] {
+ shutdownReceived = true;
+ scv.notify_one();
+ });
+ }
+ receiverConnected = socket && (name == "git://*");
+ });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket)
-// successfullyConnected2 = true;
-// cv.notify_one();
-// });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ rcv.notify_one();
+ socket->shutdown();
+ }
+ });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyNotConnected && successfullyConnected2 && receiverConnected == 1;
-// }));
-// CPPUNIT_ASSERT(aliceAccount->connectionManager().activeSockets() == 1);
-// }
-// */
-// void
-// ConnectionManagerTest::testMultipleChannelsOneDeclined()
-// {
-
-// std::condition_variable cv;
-// bool successfullyNotConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ rcv.wait_for(lk, 30s);
+ scv.wait_for(lk, 30s);
+ CPPUNIT_ASSERT(shutdownReceived);
+ CPPUNIT_ASSERT(successfullyReceive);
+ CPPUNIT_ASSERT(successfullyConnected);
+ CPPUNIT_ASSERT(receiverConnected);
+}
+void
+ConnectionManagerTest::testCloseConnectionWith()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// auto chanlReqCalBack = []
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
-// {
-// if (name == "git://*")
-// return false;
-// return true;
-// };
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// bobConMngr.onChannelRequest(chanlReqCalBack);
+ auto bobUri = bob->id.second->issuer->getId().toString();
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable rcv, scv;
+ std::atomic_int events(0);
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ successfullyReceive = name == "git://*";
+ return true;
+ });
-// auto conctReadyCalBack =[&receiverConnected]
-// (const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket)
-// receiverConnected += 1;
-// };
+ bob->connectionManager->onConnectionReady([&](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<dhtnet::ChannelSocket> socket) {
+ if (socket) {
+ socket->onShutdown([&] {
+ events += 1;
+ scv.notify_one();
+ });
+ }
+ receiverConnected = socket && (name == "git://*");
+ });
-// bobConMngr.onConnectionReady(conctReadyCalBack);
+ alice->connectionManager->connectDevice(bob->id.second->getId(),
+ "git://*",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const dht::InfoHash&) {
+ if (socket) {
+ socket->onShutdown([&] {
+ events += 1;
+ scv.notify_one();
+ });
+ successfullyConnected = true;
+ rcv.notify_one();
+ }
+ });
+ rcv.wait_for(lk, 30s);
+ // This should trigger onShutdown
+ alice->connectionManager->closeConnectionsWith(bobUri);
+ CPPUNIT_ASSERT(scv.wait_for(lk, 60s, [&] {
+ return events == 2 && successfullyReceive && successfullyConnected && receiverConnected;
+ }));
+}
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected = true;
-// cv.notify_one();
-// };
+// explain algorithm
+void
+ConnectionManagerTest::testShutdownCallbacks()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// alicConMngr.connectDevice(bobDevicId, "git://*", conctDevicCalBack);
+ auto aliceUri = alice->id.second->issuer->getId().toString();
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected2 = true;
-// cv.notify_one();
-// };
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable rcv, chan2cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
-// alicConMngr.connectDevice(bobDevicId, "sip://*", conctDevicCalBack);
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive, &chan2cv](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ if (name == "1") {
+ successfullyReceive = true;
+ } else {
+ chan2cv.notify_one();
+ // Do not return directly. Let the connection be closed
+ std::this_thread::sleep_for(10s);
+ }
+ return true;
+ });
+ bob->connectionManager->onConnectionReady([&](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<dhtnet::ChannelSocket> socket) {
+ receiverConnected = socket && (name == "1");
+ });
+ alice->connectionManager->connectDevice(bob->id.second->getId(),
+ "1",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const dht::InfoHash&) {
+ if (socket) {
+ successfullyConnected = true;
+ rcv.notify_one();
+ }
+ });
+ // Connect first channel. This will initiate a mx sock
+ CPPUNIT_ASSERT(rcv.wait_for(lk, 30s, [&] {
+ fmt::print("successfullyReceive: {}\n", successfullyReceive);
+ fmt::print("successfullyConnected: {}\n", successfullyConnected);
+ fmt::print("receiverConnected: {}\n", receiverConnected);
+ return successfullyReceive && successfullyConnected && receiverConnected;
+ }));
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyNotConnected && successfullyConnected2 && receiverConnected == 1;
-// }));
-// CPPUNIT_ASSERT(aliceAccount->connectionManager().activeSockets() == 1);
-// }
+ // Connect another channel, but close the connection
+ bool channel2NotConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second->getId(),
+ "2",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const dht::InfoHash&) {
+ channel2NotConnected = !socket;
+ rcv.notify_one();
+ });
+ chan2cv.wait_for(lk, 30s);
-// /*
-// void
-// ConnectionManagerTest::testMultipleChannelsSameName()
-// {
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ // This should trigger onShutdown for second callback
+ bob->connectionManager->closeConnectionsWith(aliceUri);
+ CPPUNIT_ASSERT(rcv.wait_for(lk, 30s, [&] { return channel2NotConnected; }));
+}
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+void
+ConnectionManagerTest::testFloodSocket()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string&,
-// std::shared_ptr<ChannelSocket> socket) {
-// if (socket)
-// receiverConnected += 1;
-// });
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
+ std::shared_ptr<dhtnet::ChannelSocket> rcvSock1, rcvSock2, rcvSock3, sendSock, sendSock2,
+ sendSock3;
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ successfullyReceive = name == "1";
+ return true;
+ });
+ bob->connectionManager->onConnectionReady([&](const DeviceId&,
+ const std::string& name,
+ std::shared_ptr<dhtnet::ChannelSocket> socket) {
+ receiverConnected = socket != nullptr;
+ if (name == "1")
+ rcvSock1 = socket;
+ else if (name == "2")
+ rcvSock2 = socket;
+ else if (name == "3")
+ rcvSock3 = socket;
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "1",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
+ return successfullyReceive && successfullyConnected && receiverConnected;
+ }));
+ CPPUNIT_ASSERT(receiverConnected);
+ successfullyConnected = false;
+ receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "2",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock2 = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
+ successfullyConnected = false;
+ receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "3",
+ [&](std::shared_ptr<dhtnet::ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock3 = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
+ std::mutex mtxRcv {};
+ std::string alphabet, shouldRcv, rcv1, rcv2, rcv3;
+ for (int i = 0; i < 100; ++i)
+ alphabet += "QWERTYUIOPASDFGHJKLZXCVBNM";
+ rcvSock1->setOnRecv([&](const uint8_t* buf, size_t len) {
+ rcv1 += std::string(buf, buf + len);
+ return len;
+ });
+ rcvSock2->setOnRecv([&](const uint8_t* buf, size_t len) {
+ rcv2 += std::string(buf, buf + len);
+ return len;
+ });
+ rcvSock3->setOnRecv([&](const uint8_t* buf, size_t len) {
+ rcv3 += std::string(buf, buf + len);
+ return len;
+ });
+ for (uint64_t i = 0; i < alphabet.size(); ++i) {
+ auto send = std::string(8000, alphabet[i]);
+ shouldRcv += send;
+ std::error_code ec;
+ sendSock->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ sendSock2->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ sendSock3->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ CPPUNIT_ASSERT(!ec);
+ }
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
+ return shouldRcv == rcv1 && shouldRcv == rcv2 && shouldRcv == rcv3;
+ }));
+}
-// // We can open two sockets with the same name, it will be two different channel
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected2 = true;
-// }
-// cv.notify_one();
-// });
+void
+ConnectionManagerTest::testDestroyWhileSending()
+{
+ // Same as test before, but destroy the accounts while sending.
+ // This test if a segfault occurs
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
+ bool successfullyReceive = false;
+ bool receiverConnected = false;
+ std::shared_ptr<ChannelSocket> rcvSock1, rcvSock2, rcvSock3, sendSock, sendSock2, sendSock3;
+ bob->connectionManager->onChannelRequest(
+ [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
+ const std::string& name) {
+ successfullyReceive = name == "1";
+ return true;
+ });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
+ receiverConnected = socket != nullptr;
+ if (name == "1")
+ rcvSock1 = socket;
+ else if (name == "2")
+ rcvSock2 = socket;
+ else if (name == "3")
+ rcvSock3 = socket;
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "1",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
+ return successfullyReceive && successfullyConnected && receiverConnected;
+ }));
+ successfullyConnected = false;
+ receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "2",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock2 = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
+ successfullyConnected = false;
+ receiverConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "3",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ sendSock3 = socket;
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
+ std::mutex mtxRcv {};
+ std::string alphabet;
+ for (int i = 0; i < 100; ++i)
+ alphabet += "QWERTYUIOPASDFGHJKLZXCVBNM";
+ rcvSock1->setOnRecv([&](const uint8_t*, size_t len) { return len; });
+ rcvSock2->setOnRecv([&](const uint8_t*, size_t len) { return len; });
+ rcvSock3->setOnRecv([&](const uint8_t*, size_t len) { return len; });
+ for (uint64_t i = 0; i < alphabet.size(); ++i) {
+ auto send = std::string(8000, alphabet[i]);
+ std::error_code ec;
+ sendSock->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ sendSock2->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ sendSock3->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
+ CPPUNIT_ASSERT(!ec);
+ }
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
-// }));
-// }
-// */
-// void
-// ConnectionManagerTest::testMultipleChannelsSameName()
-// {
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyConnected2 = false;
-// int receiverConnected = 0;
+ // No need to wait, immediately destroy, no segfault must occurs
+}
+void
+ConnectionManagerTest::testIsConnecting()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// auto chanlReqCalBack = []
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
-// {
-// return true;
-// };
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false, successfullyReceive = false;
-// bobConMngr.onChannelRequest(chanlReqCalBack);
+ bob->connectionManager->onChannelRequest(
+ [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) {
+ successfullyReceive = true;
+ cv.notify_one();
+ std::this_thread::sleep_for(2s);
+ return true;
+ });
+ CPPUNIT_ASSERT(!alice->connectionManager->isConnecting(bob->id.second->getLongId(), "sip"));
-// auto conctReadyCalBack =[&receiverConnected]
-// (const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket)
-// receiverConnected += 1;
-// };
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // connectDevice is full async, so isConnecting will be true after a few ms.
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyReceive; }));
+ CPPUNIT_ASSERT(alice->connectionManager->isConnecting(bob->id.second->getLongId(), "sip"));
+ CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyConnected; }));
+ std::this_thread::sleep_for(
+ std::chrono::milliseconds(100)); // Just to wait for the callback to finish
+ CPPUNIT_ASSERT(!alice->connectionManager->isConnecting(bob->id.second->getLongId(), "sip"));
+}
-// bobConMngr.onConnectionReady(conctReadyCalBack);
+void
+ConnectionManagerTest::testCanSendBeacon()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected = true;
-// cv.notify_one();
-// };
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
-// alicConMngr.connectDevice(bobDevicId, "git://*", conctDevicCalBack);
+ std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
+ bob->connectionManager->onChannelRequest(
+ [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && socket->name() == "sip")
+ bobSocket = socket->underlyingSocket();
+ cv.notify_one();
+ });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ aliceSocket = socket->underlyingSocket();
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // connectDevice is full async, so isConnecting will be true after a few ms.
+ CPPUNIT_ASSERT(
+ cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket && successfullyConnected; }));
+ CPPUNIT_ASSERT(aliceSocket->canSendBeacon());
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket)
-// successfullyConnected2 = true;
-// cv.notify_one();
-// };
+ // Because onConnectionReady is true before version is sent, we can wait a bit
+ // before canSendBeacon is true.
+ auto start = std::chrono::steady_clock::now();
+ auto aliceCanSendBeacon = false;
+ auto bobCanSendBeacon = false;
+ do {
+ aliceCanSendBeacon = aliceSocket->canSendBeacon();
+ bobCanSendBeacon = bobSocket->canSendBeacon();
+ if (!bobCanSendBeacon || !aliceCanSendBeacon)
+ std::this_thread::sleep_for(1s);
+ } while ((not bobCanSendBeacon or not aliceCanSendBeacon)
+ and std::chrono::steady_clock::now() - start < 5s);
-// alicConMngr.connectDevice(bobDevicId, "sip://*", conctDevicCalBack);
+ CPPUNIT_ASSERT(bobCanSendBeacon && aliceCanSendBeacon);
+}
+void
+ConnectionManagerTest::testCannotSendBeacon()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return successfullyConnected && successfullyConnected2 && receiverConnected == 2;
-// }));
-// }
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// //Explain this more
-// /*
-// void
-// ConnectionManagerTest::testSendReceiveData()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
+ bob->connectionManager->onChannelRequest(
+ [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && socket->name() == "sip")
+ bobSocket = socket->underlyingSocket();
+ cv.notify_one();
+ });
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// std::atomic_int events(0);
-// bool successfullyConnected = false, successfullyConnected2 = false, successfullyReceive = false,
-// receiverConnected = false;
-// const uint8_t buf_other[] = {0x64, 0x65, 0x66, 0x67};
-// const uint8_t buf_test[] = {0x68, 0x69, 0x70, 0x71};
-// bool dataOk = false, dataOk2 = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ aliceSocket = socket->underlyingSocket();
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // connectDevice is full async, so isConnecting will be true after a few ms.
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string&) {
-// successfullyReceive = true;
-// return true;
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && (name == "test" || name == "other")) {
-// receiverConnected = true;
-// std::error_code ec;
-// auto res = socket->waitForData(std::chrono::milliseconds(5000), ec);
-// if (res == 4) {
-// uint8_t buf[4];
-// socket->read(&buf[0], 4, ec);
-// if (name == "test")
-// dataOk = std::equal(std::begin(buf), std::end(buf), std::begin(buf_test));
-// else
-// dataOk2 = std::equal(std::begin(buf), std::end(buf), std::begin(buf_other));
-// events++;
-// cv.notify_one();
-// }
-// }
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "test",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// std::error_code ec;
-// socket->write(&buf_test[0], 4, ec);
-// }
-// events++;
-// cv.notify_one();
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "other",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected2 = true;
-// std::error_code ec;
-// socket->write(&buf_other[0], 4, ec);
-// }
-// events++;
-// cv.notify_one();
-// });
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return events == 4 && successfullyReceive && successfullyConnected && successfullyConnected2
-// && dataOk && dataOk2;
-// }));
-// }
-// */
-// void
-// ConnectionManagerTest::testSendReceiveData()
-// {
-
-// std::condition_variable cv;
-// std::atomic_int events(0);
-// bool successfullyConnected = false;
-// bool successfullyConnected2 = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// const uint8_t buf_other[] = {0x64, 0x65, 0x66, 0x67};
-// const uint8_t buf_test[] = {0x68, 0x69, 0x70, 0x71};
-// bool dataOk = false;
-// bool dataOk2 = false;
-
-
-// auto chanlReqCalBack = [&successfullyReceive]
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string&)
-// {
-// successfullyReceive = true;
-// return true;
-// };
-
-// bobConMngr.onChannelRequest(chanlReqCalBack);
-
-
-// auto conctReadyCalBack =[&]
-// (const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket && (name == "test" || name == "other")) {
-// receiverConnected = true;
-// std::error_code ec;
-// auto res = socket->waitForData(std::chrono::milliseconds(5000), ec);
-// if (res == 4) {
-// uint8_t buf[4];
-// socket->read(&buf[0], 4, ec);
-// if (name == "test")
-// dataOk = std::equal(std::begin(buf), std::end(buf), std::begin(buf_test));
-// else
-// dataOk2 = std::equal(std::begin(buf), std::end(buf), std::begin(buf_other));
-// events++;
-// cv.notify_one();
-// }
-// }
-// };
-
-// bobConMngr.onConnectionReady(conctReadyCalBack);
-
-
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket) {
-// successfullyConnected = true;
-// std::error_code ec;
-// socket->write(&buf_test[0], 4, ec);
-// }
-// events++;
-// cv.notify_one();
-// };
-
-
-// alicConMngr.connectDevice(bobDevicId, "test", conctDevicCalBack);
-
-
-// auto conctDevicCalBack2 = [&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket) {
-// successfullyConnected2 = true;
-// std::error_code ec;
-// socket->write(&buf_other[0], 4, ec);
-// }
-// events++;
-// cv.notify_one();
-// };
-
-// alicConMngr.connectDevice(bobDevicId, "other", conctDevicCalBack2);
-
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return events == 4 && successfullyReceive && successfullyConnected && successfullyConnected2
-// && dataOk && dataOk2;
-// }));
-// }
-
-
-
-// /* void
-// ConnectionManagerTest::testAcceptsICERequest()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onICERequest([&](const DeviceId&) {
-// successfullyReceive = true;
-// return true;
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string& name,
-// std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket && (name == "git://*");
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-// } */
-// void
-// ConnectionManagerTest::testAcceptsICERequest()
-// {
-
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-
-// bobAccount->connectionManager().onICERequest([&](const DeviceId&) {
-// successfullyReceive = true;
-// return true;
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string& name,
-// std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket && (name == "git://*");
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-// }
-
-// /* void
-// ConnectionManagerTest::testDeclineICERequest()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onICERequest([&](const DeviceId&) {
-// successfullyReceive = true;
-// return false;
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string& name,
-// std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket && (name == "git://*");
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-
-// cv.wait_for(lk, 30s);
-// CPPUNIT_ASSERT(successfullyReceive);
-// CPPUNIT_ASSERT(!receiverConnected);
-// CPPUNIT_ASSERT(!successfullyConnected);
-// } */
-
-// //why you invoke other functions when you want to test ICErequest?
-// void
-// ConnectionManagerTest::testDeclineICERequest()
-// {
-
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-
-// bobAccount->connectionManager().onICERequest([&](const DeviceId&) {
-// successfullyReceive = true;
-// return false; //???????????????????????? is this the point?
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&receiverConnected](const DeviceId&,
-// const std::string& name,
-// std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket && (name == "git://*");
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-
-// cv.wait_for(lk, 30s);
-// CPPUNIT_ASSERT(successfullyReceive);
-// CPPUNIT_ASSERT(!receiverConnected);
-// CPPUNIT_ASSERT(!successfullyConnected);
-// }
-
-// //I think you testing something other than the current class!
-// /*
-// void
-// ConnectionManagerTest::testChannelRcvShutdown()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool shutdownReceived = false;
-
-// std::shared_ptr<ChannelSocket> bobSock;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId& did, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && name == "git://*" && did != bobDeviceId) {
-// bobSock = socket;
-// cv.notify_one();
-// }
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// socket->onShutdown([&] {
-// shutdownReceived = true;
-// cv.notify_one();
-// });
-// successfullyConnected = true;
-// cv.notify_one();
-// }
-// });
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return bobSock && successfullyConnected; }));
-// bobSock->shutdown();
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return shutdownReceived; }));
-// }
-// */
-// void
-// ConnectionManagerTest::testChannelRcvShutdown()
-// {
-
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool shutdownReceived = false;
-
-// std::shared_ptr<ChannelSocket> bobSock;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId& did, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && name == "git://*" && did != bobDeviceId) {
-// bobSock = socket;
-// cv.notify_one();
-// }
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// socket->onShutdown([&] {
-// shutdownReceived = true;
-// cv.notify_one();
-// });
-// successfullyConnected = true;
-// cv.notify_one();
-// }
-// });
-
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return bobSock && successfullyConnected; }));
-
-// bobSock->shutdown();
-
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return shutdownReceived; }));
-// }
-
-// //I think you testing something other than the current class!
-// void
-// ConnectionManagerTest::testChannelSenderShutdown()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable rcv, scv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-// bool shutdownReceived = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string& name) {
-// successfullyReceive = name == "git://*";
-// return true;
-// });
-
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// if (socket) {
-// socket->onShutdown([&] {
-// shutdownReceived = true;
-// scv.notify_one();
-// });
-// }
-// receiverConnected = socket && (name == "git://*");
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// rcv.notify_one();
-// socket->shutdown();
-// }
-// });
-
-// rcv.wait_for(lk, 30s);
-// scv.wait_for(lk, 30s);
-// CPPUNIT_ASSERT(shutdownReceived);
-// CPPUNIT_ASSERT(successfullyReceive);
-// CPPUNIT_ASSERT(successfullyConnected);
-// CPPUNIT_ASSERT(receiverConnected);
-// }
-
-// //how to get URI?
-// //The call back function has different logic. Also, there are cuncurrenct tasks here. Please explain them.
-// void
-// ConnectionManagerTest::testCloseConnectionWith()
-// {
-
-
-// auto bobUri = bobAccount->getUsername();
-
-// std::condition_variable rcv, scv;
-// std::atomic_int events(0);
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// auto chanlReqCalBack = [&successfullyReceive]
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
-// {
-// successfullyReceive = name == "git://*";
-// return true;
-// };
-
-// bobConMngr.onChannelRequest(chanlReqCalBack);
-
-
-// auto conctReadyCalBack =[&]
-// (const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket)
-// {
-// if (socket) {
-// socket->onShutdown([&] {
-// events += 1;// this is an atomic variable why not using atomic operation i.e event.fetch_add(1)
-// scv.notify_one();
-// });
-// }
-// receiverConnected = socket && (name == "git://*");
-// }
-
-// bobConMngr.onConnectionReady(conctReadyCalBack);
-
-
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket,const DeviceId&)
-// {
-// if (socket) {
-// socket->onShutdown([&] {
-// events += 1;
-// scv.notify_one();
-// });
-// successfullyConnected = true;
-// rcv.notify_one();
-// }
-// };
-
-// alicConMngr.connectDevice(bobDevicId, "git://*", conctDevicCalBack);
-
-
-// CPPUNIT_ASSERT(rcv.wait_for(lk, 60s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-
-// // This should trigger onShutdown
-// alicConMngr.closeConnectionsWith(bobUri);
-
-// CPPUNIT_ASSERT(scv.wait_for(lk, 60s, [&] {
-// return events == 2;
-// }));
-// }
-
-// //explain algorithm
-// void
-// ConnectionManagerTest::testShutdownCallbacks()
-// {
-
-// auto aliceUri = aliceAccount->getUsername();
-
-// std::condition_variable rcv, chan2cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-
-// auto chanlReqCalBack = [&successfullyReceive, &chan2cv]
-// (const std::shared_ptr<dht::crypto::Certificate>&, const std::string& name)
-// {
-// if (name == "1") {
-// successfullyReceive = true;
-// } else {
-// chan2cv.notify_one();
-// // Do not return directly. Let the connection be closed
-// std::this_thread::sleep_for(10s);
-// }
-// return true;
-// };
-
-// bobConMngr.onChannelRequest(chanlReqCalBack);
-
-
-// auto conctReadyCalBack =[&]
-// (const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket)
-// {
-// receiverConnected = socket && (name == "1");
-// };
-
-// bobConMngr.onConnectionReady(conctReadyCalBack);
-
-
-// auto conctDevicCalBack =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// if (socket) {
-// successfullyConnected = true;
-// rcv.notify_one();
-// }
-// };
-
-// alicConMngr.connectDevice(bobDeviceId, "1", conctDevicCalBack);
-
-
-// // Connect first channel. This will initiate a mx sock ?????????????????????????????????????????????????????
-// CPPUNIT_ASSERT(rcv.wait_for(lk, 30s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-
-// // Connect another channel, but close the connection
-// bool channel2NotConnected = false;
-
-
-// auto conctDevicCalBack2 =[&]
-// (std::shared_ptr<ChannelSocket> socket, const DeviceId&)
-// {
-// channel2NotConnected = !socket;
-// rcv.notify_one();
-// };
-
-// alicConMngr.connectDevice(bobDeviceId, "2", conctDevicCalBack2);
-
-// chan2cv.wait_for(lk, 30s);
-
-// // This should trigger onShutdown for second callback
-// bobConMngr.closeConnectionsWith(aliceUri);
-// CPPUNIT_ASSERT(rcv.wait_for(lk, 30s, [&] { return channel2NotConnected; }));
-// }
-
-// //What is the story?
-// void
-// ConnectionManagerTest::testFloodSocket()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-// std::shared_ptr<ChannelSocket> rcvSock1, rcvSock2, rcvSock3, sendSock, sendSock2, sendSock3;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string& name) {
-// successfullyReceive = name == "1";
-// return true;
-// });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket != nullptr;
-// if (name == "1")
-// rcvSock1 = socket;
-// else if (name == "2")
-// rcvSock2 = socket;
-// else if (name == "3")
-// rcvSock3 = socket;
-// });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "1",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-// CPPUNIT_ASSERT(receiverConnected);
-// successfullyConnected = false;
-// receiverConnected = false;
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "2",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock2 = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
-// successfullyConnected = false;
-// receiverConnected = false;
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "3",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock3 = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
-
-// std::mutex mtxRcv {};
-// std::string alphabet, shouldRcv, rcv1, rcv2, rcv3;
-// for (int i = 0; i < 100; ++i)
-// alphabet += "QWERTYUIOPASDFGHJKLZXCVBNM";
-
-// // Qx8000
-// // Wx8000
-// // Ex8000
-// // ...
-// // Qx8000
-// // Wx8000
-// // Ex8000
-// // ... x 99
-// rcvSock1->setOnRecv([&](const uint8_t* buf, size_t len) {
-// rcv1 += std::string(buf, buf + len);
-// return len;
-// });
-// rcvSock2->setOnRecv([&](const uint8_t* buf, size_t len) {
-// rcv2 += std::string(buf, buf + len);
-// return len;
-// });
-// rcvSock3->setOnRecv([&](const uint8_t* buf, size_t len) {
-// rcv3 += std::string(buf, buf + len);
-// return len;
-// });
-// for (uint64_t i = 0; i < alphabet.size(); ++i) {
-// auto send = std::string(8000, alphabet[i]);
-// shouldRcv += send;
-// std::error_code ec;
-// sendSock->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// sendSock2->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// sendSock3->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// CPPUNIT_ASSERT(!ec);
-// }
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] {
-// return shouldRcv == rcv1 && shouldRcv == rcv2 && shouldRcv == rcv3;
-// }));
-// }
-
-// void
-// ConnectionManagerTest::testDestroyWhileSending()
-// {
-// // Same as test before, but destroy the accounts while sending.
-// // This test if a segfault occurs
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-// bool receiverConnected = false;
-// std::shared_ptr<ChannelSocket> rcvSock1, rcvSock2, rcvSock3, sendSock, sendSock2, sendSock3;
-// bobAccount->connectionManager().onChannelRequest(
-// [&successfullyReceive](const std::shared_ptr<dht::crypto::Certificate>&,
-// const std::string& name) {
-// successfullyReceive = name == "1";
-// return true;
-// });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string& name, std::shared_ptr<ChannelSocket> socket) {
-// receiverConnected = socket != nullptr;
-// if (name == "1")
-// rcvSock1 = socket;
-// else if (name == "2")
-// rcvSock2 = socket;
-// else if (name == "3")
-// rcvSock3 = socket;
-// });
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "1",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] {
-// return successfullyReceive && successfullyConnected && receiverConnected;
-// }));
-// successfullyConnected = false;
-// receiverConnected = false;
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "2",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock2 = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
-// successfullyConnected = false;
-// receiverConnected = false;
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "3",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// sendSock3 = socket;
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyConnected && receiverConnected; }));
-// std::mutex mtxRcv {};
-// std::string alphabet;
-// for (int i = 0; i < 100; ++i)
-// alphabet += "QWERTYUIOPASDFGHJKLZXCVBNM";
-// rcvSock1->setOnRecv([&](const uint8_t*, size_t len) { return len; });
-// rcvSock2->setOnRecv([&](const uint8_t*, size_t len) { return len; });
-// rcvSock3->setOnRecv([&](const uint8_t*, size_t len) { return len; });
-// for (uint64_t i = 0; i < alphabet.size(); ++i) {
-// auto send = std::string(8000, alphabet[i]);
-// std::error_code ec;
-// sendSock->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// sendSock2->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// sendSock3->write(reinterpret_cast<unsigned char*>(send.data()), send.size(), ec);
-// CPPUNIT_ASSERT(!ec);
-// }
-
-
-
-// // No need to wait, immediately destroy, no segfault must occurs
-// }
-
-
-// //why you don't use this function in other test units to validate a test?
-// /*
-// void
-// ConnectionManagerTest::testIsConnecting()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false, successfullyReceive = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) {
-// successfullyReceive = true;
-// cv.notify_one();
-// std::this_thread::sleep_for(2s);
-// return true;
-// });
-
-// CPPUNIT_ASSERT(!aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyReceive; }));
-// CPPUNIT_ASSERT(aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyConnected; }));
-// std::this_thread::sleep_for(
-// std::chrono::milliseconds(100)); // Just to wait for the callback to finish
-// CPPUNIT_ASSERT(!aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-// }
-// */
-// void
-// ConnectionManagerTest::testIsConnecting()
-// {
-
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-// bool successfullyReceive = false;
-
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) {
-// successfullyReceive = true;
-// cv.notify_one();
-// std::this_thread::sleep_for(2s);
-// return true;
-// });
-
-// CPPUNIT_ASSERT(!aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyReceive; }));
-// CPPUNIT_ASSERT(aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-// CPPUNIT_ASSERT(cv.wait_for(lk, 60s, [&] { return successfullyConnected; }));
-// std::this_thread::sleep_for(
-// std::chrono::milliseconds(100)); // Just to wait for the callback to finish
-// CPPUNIT_ASSERT(!aliceAccount->connectionManager().isConnecting(bobDeviceId, "sip"));
-// }
-
-
-
-// void
-// ConnectionManagerTest::testCanSendBeacon()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-
-// std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && socket->name() == "sip")
-// bobSocket = socket->underlyingSocket();
-// cv.notify_one();
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// aliceSocket = socket->underlyingSocket();
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket && successfullyConnected; }));
-// CPPUNIT_ASSERT(aliceSocket->canSendBeacon());
-
-// // Because onConnectionReady is true before version is sent, we can wait a bit
-// // before canSendBeacon is true.
-// auto start = std::chrono::steady_clock::now();
-// auto aliceCanSendBeacon = false;
-// auto bobCanSendBeacon = false;
-// do {
-// aliceCanSendBeacon = aliceSocket->canSendBeacon();
-// bobCanSendBeacon = bobSocket->canSendBeacon();
-// if (!bobCanSendBeacon || !aliceCanSendBeacon)
-// std::this_thread::sleep_for(1s);
-// } while ((not bobCanSendBeacon or not aliceCanSendBeacon)
-// and std::chrono::steady_clock::now() - start < 5s);
-
-// CPPUNIT_ASSERT(bobCanSendBeacon && aliceCanSendBeacon);
-// }
-
-// void
-// ConnectionManagerTest::testCannotSendBeacon()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
-
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
-
-// std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && socket->name() == "sip")
-// bobSocket = socket->underlyingSocket();
-// cv.notify_one();
-// });
-
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// aliceSocket = socket->underlyingSocket();
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
+ int version = 1412;
+ bobSocket->setOnVersionCb([&](auto v) {
+ version = v;
+ cv.notify_one();
+ });
+ aliceSocket->setVersion(0);
+ aliceSocket->sendVersion();
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return version == 0; }));
+ CPPUNIT_ASSERT(!bobSocket->canSendBeacon());
+}
-// int version = 1412;
-// bobSocket->setOnVersionCb([&](auto v) {
-// version = v;
-// cv.notify_one();
-// });
-// aliceSocket->setVersion(0);
-// aliceSocket->sendVersion();
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return version == 0; }));
-// CPPUNIT_ASSERT(!bobSocket->canSendBeacon());
-// }
+void
+ConnectionManagerTest::testConnectivityChangeTriggerBeacon()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
-// void
-// ConnectionManagerTest::testConnectivityChangeTriggerBeacon()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
+ std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
+ bob->connectionManager->onChannelRequest(
+ [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && socket->name() == "sip")
+ bobSocket = socket->underlyingSocket();
+ cv.notify_one();
+ });
-// std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && socket->name() == "sip")
-// bobSocket = socket->underlyingSocket();
-// cv.notify_one();
-// });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ aliceSocket = socket->underlyingSocket();
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // connectDevice is full async, so isConnecting will be true after a few ms.
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// aliceSocket = socket->underlyingSocket();
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
+ bool hasRequest = false;
+ bobSocket->setOnBeaconCb([&](auto p) {
+ if (p)
+ hasRequest = true;
+ cv.notify_one();
+ });
+ alice->connectionManager->connectivityChanged();
+ CPPUNIT_ASSERT(cv.wait_for(lk, 10s, [&] { return hasRequest; }));
+}
-// bool hasRequest = false;
-// bobSocket->setOnBeaconCb([&](auto p) {
-// if (p)
-// hasRequest = true;
-// cv.notify_one();
-// });
-// aliceAccount->connectionManager().connectivityChanged();
-// CPPUNIT_ASSERT(cv.wait_for(lk, 10s, [&] { return hasRequest; }));
-// }
+void
+ConnectionManagerTest::testOnNoBeaconTriggersShutdown()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey()); //
-// void
-// ConnectionManagerTest::testOnNoBeaconTriggersShutdown()
-// {
-// auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId);
-// auto bobAccount = Manager::instance().getAccount<JamiAccount>(bobId);
-// auto bobDeviceId = DeviceId(std::string(bobAccount->currentDeviceId()));
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
-// bobAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyConnected = false;
-// std::mutex mtx;
-// std::unique_lock<std::mutex> lk {mtx};
-// std::condition_variable cv;
-// bool successfullyConnected = false;
+ std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
+ bob->connectionManager->onChannelRequest(
+ [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket && socket->name() == "sip")
+ bobSocket = socket->underlyingSocket();
+ cv.notify_one();
+ });
-// std::shared_ptr<MultiplexedSocket> aliceSocket, bobSocket;
-// bobAccount->connectionManager().onChannelRequest(
-// [&](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
-// bobAccount->connectionManager().onConnectionReady(
-// [&](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
-// if (socket && socket->name() == "sip")
-// bobSocket = socket->underlyingSocket();
-// cv.notify_one();
-// });
+ alice->connectionManager->connectDevice(bob->id.second,
+ "sip",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ aliceSocket = socket->underlyingSocket();
+ successfullyConnected = true;
+ }
+ cv.notify_one();
+ });
+ // connectDevice is full async, so isConnecting will be true after a few ms.
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "sip",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// if (socket) {
-// aliceSocket = socket->underlyingSocket();
-// successfullyConnected = true;
-// }
-// cv.notify_one();
-// });
-// // connectDevice is full async, so isConnecting will be true after a few ms.
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return aliceSocket && bobSocket; }));
+ bool isClosed = false;
+ aliceSocket->onShutdown([&] {
+ isClosed = true;
+ cv.notify_one();
+ });
+ bobSocket->answerToBeacon(false);
+ alice->connectionManager->connectivityChanged();
+ CPPUNIT_ASSERT(cv.wait_for(lk, 10s, [&] { return isClosed; }));
+}
-// bool isClosed = false;
-// aliceSocket->onShutdown([&] {
-// isClosed = true;
-// cv.notify_one();
-// });
-// bobSocket->answerToBeacon(false);
-// aliceAccount->connectionManager().connectivityChanged();
-// CPPUNIT_ASSERT(cv.wait_for(lk, 10s, [&] { return isClosed; }));*/
-// }
+void
+ConnectionManagerTest::testShutdownWhileNegotiating()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
+ alice->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::unique_lock<std::mutex> lk {mtx};
+ std::condition_variable cv;
+ bool successfullyReceive = false;
+ bool notConnected = false;
-// //why you didn't invoke on Channel request?
-// void
-// ConnectionManagerTest::testShutdownWhileNegotiating()
-// {
+ bob->connectionManager->onICERequest([&](const DeviceId&) {
+ successfullyReceive = true;
+ cv.notify_one();
+ return true;
+ });
-// std::condition_variable cv;
-// bool successfullyReceive = false;
-// bool notConnected = false;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ notConnected = !socket;
+ cv.notify_one();
+ });
-// aliceAccount->connectionManager().onICERequest([](const DeviceId&) { return true; });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyReceive; }));
+ // Manager::instance().setAccountActive(alice->id.second, false, true);
-// //Why???????????
-// bobAccount->connectionManager().onICERequest([&](const DeviceId&) {
-// successfullyReceive = true;
-// cv.notify_one();
-// return true;
-// });
+ // Just move destruction on another thread.
+ // dht::threadpool::io().run([conMgr =std::move(alice->connectionManager)] {});
+ alice->connectionManager.reset();
-// aliceAccount->connectionManager().connectDevice(bobDeviceId,
-// "git://*",
-// [&](std::shared_ptr<ChannelSocket> socket,
-// const DeviceId&) {
-// notConnected = !socket;
-// cv.notify_one();
-// });
+ CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return notConnected; }));
+}
+void
+ConnectionManagerTest::testGetChannelList()
+{
+ alice->connectionManager->onDhtConnected(alice->id.first->getPublicKey());
+ bob->connectionManager->onDhtConnected(bob->id.first->getPublicKey());
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return successfullyReceive; }));
-
+ bob->connectionManager->onICERequest([](const DeviceId&) { return true; });
+ std::mutex mtx;
+ std::condition_variable cv;
+ std::unique_lock<std::mutex> lk {mtx};
+ bool successfullyConnected = false;
+ int receiverConnected = 0;
+ bob->connectionManager->onChannelRequest(
+ [](const std::shared_ptr<dht::crypto::Certificate>&, const std::string&) { return true; });
+ bob->connectionManager->onConnectionReady(
+ [&receiverConnected,
+ &cv](const DeviceId&, const std::string&, std::shared_ptr<ChannelSocket> socket) {
+ if (socket)
+ receiverConnected += 1;
-// aliceAccount->connectionManager().reset(); //use it but check it first
-// Manager::instance().setAccountActive(aliceId, false, true);//?????????????????????????????????????
+ cv.notify_one();
+ });
+ std::string channelId;
+ alice->connectionManager->connectDevice(bob->id.second,
+ "git://*",
+ [&](std::shared_ptr<ChannelSocket> socket,
+ const DeviceId&) {
+ if (socket) {
+ channelId = std::to_string(socket->channel());
+ successfullyConnected = true;
+ }
-// CPPUNIT_ASSERT(cv.wait_for(lk, 30s, [&] { return notConnected; }));
-// }
+ cv.notify_one();
+ });
+ CPPUNIT_ASSERT(
+ cv.wait_for(lk, 60s, [&] { return successfullyConnected && receiverConnected == 1; }));
+ std::vector<std::map<std::string, std::string>> expectedList = {
+ {{"channel", channelId}, {"channelName", "git://*"}}};
+ auto connectionList = alice->connectionManager->getConnectionList();
+ CPPUNIT_ASSERT(!connectionList.empty());
+ const auto& connectionInfo = connectionList[0];
+ auto it = connectionInfo.find("id");
+ CPPUNIT_ASSERT(it != connectionInfo.end());
+ std::string connectionId = it->second;
+ auto actualList = alice->connectionManager->getChannelList(connectionId);
+ CPPUNIT_ASSERT(expectedList.size() == actualList.size());
+ CPPUNIT_ASSERT(std::equal(expectedList.begin(), expectedList.end(), actualList.begin()));
+ for (const auto& expectedMap : expectedList) {
+ auto it = std::find_if(actualList.begin(),
+ actualList.end(),
+ [&](const std::map<std::string, std::string>& actualMap) {
+ return expectedMap.size() == actualMap.size()
+ && std::equal(expectedMap.begin(),
+ expectedMap.end(),
+ actualMap.begin());
+ });
+ CPPUNIT_ASSERT(it != actualList.end());
+ }
+}
} // namespace test
} // namespace dhtnet