Line data Source code
1 : /* 2 : * Copyright (C) 2004-2024 Savoir-faire Linux Inc. 3 : * 4 : * This program is free software: you can redistribute it and/or modify 5 : * it under the terms of the GNU General Public License as published by 6 : * the Free Software Foundation, either version 3 of the License, or 7 : * (at your option) any later version. 8 : * 9 : * This program is distributed in the hope that it will be useful, 10 : * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 : * GNU General Public License for more details. 13 : * 14 : * You should have received a copy of the GNU General Public License 15 : * along with this program. If not, see <https://www.gnu.org/licenses/>. 16 : */ 17 : 18 : #include <cppunit/TestAssert.h> 19 : #include <cppunit/TestFixture.h> 20 : #include <cppunit/extensions/HelperMacros.h> 21 : 22 : #include <condition_variable> 23 : #include <string> 24 : #include <fstream> 25 : #include <streambuf> 26 : 27 : #include "manager.h" 28 : #include "jamidht/jamiaccount.h" 29 : #include "../../test_runner.h" 30 : #include "jami.h" 31 : #include "fileutils.h" 32 : #include "account_const.h" 33 : #include "common.h" 34 : 35 : using namespace std::string_literals; 36 : using namespace libjami::Account; 37 : 38 : namespace jami { 39 : namespace test { 40 : 41 : class RevokeTest : public CppUnit::TestFixture 42 : { 43 : public: 44 2 : RevokeTest() 45 2 : { 46 : // Init daemon 47 2 : libjami::init(libjami::InitFlag(libjami::LIBJAMI_FLAG_DEBUG | libjami::LIBJAMI_FLAG_CONSOLE_LOG)); 48 2 : if (not Manager::instance().initialized) 49 1 : CPPUNIT_ASSERT(libjami::start("dring-sample.yml")); 50 2 : } 51 4 : ~RevokeTest() { libjami::fini(); } 52 2 : static std::string name() { return "Revoke"; } 53 : void setUp(); 54 : void tearDown(); 55 : 56 : std::string aliceId; 57 : std::string bobId; 58 : 59 : private: 60 : void testRevokeDevice(); 61 : void testRevokeInvalidDevice(); 62 : 63 2 : CPPUNIT_TEST_SUITE(RevokeTest); 64 1 : CPPUNIT_TEST(testRevokeDevice); 65 1 : CPPUNIT_TEST(testRevokeInvalidDevice); 66 4 : CPPUNIT_TEST_SUITE_END(); 67 : }; 68 : 69 : CPPUNIT_TEST_SUITE_NAMED_REGISTRATION(RevokeTest, RevokeTest::name()); 70 : 71 : void 72 2 : RevokeTest::setUp() 73 : { 74 4 : auto actors = load_actors_and_wait_for_announcement("actors/alice-bob-password.yml"); 75 2 : aliceId = actors["alice"]; 76 2 : bobId = actors["bob"]; 77 2 : } 78 : 79 : void 80 2 : RevokeTest::tearDown() 81 : { 82 6 : wait_for_removal_of({aliceId, bobId}); 83 2 : } 84 : 85 : void 86 1 : RevokeTest::testRevokeDevice() 87 : { 88 1 : auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId); 89 : 90 1 : CPPUNIT_ASSERT(aliceAccount->exportArchive("test.gz")); 91 : 92 2 : std::map<std::string, std::string> details = libjami::getAccountTemplate("RING"); 93 1 : details[ConfProperties::ARCHIVE_PATH] = "test.gz"; 94 : 95 1 : std::mutex mtx; 96 1 : std::unique_lock lk {mtx}; 97 1 : std::condition_variable cv; 98 1 : std::map<std::string, std::shared_ptr<libjami::CallbackWrapperBase>> confHandlers; 99 1 : auto deviceRevoked = false; 100 1 : auto knownChanged = false; 101 1 : std::string alice2Device; 102 1 : confHandlers.insert( 103 2 : libjami::exportable_callback<libjami::ConfigurationSignal::DeviceRevocationEnded>( 104 1 : [&](const std::string& accountId, const std::string& deviceId, int status) { 105 1 : if (accountId == aliceId && deviceId == alice2Device && status == 0) 106 1 : deviceRevoked = true; 107 1 : cv.notify_one(); 108 1 : })); 109 1 : confHandlers.insert(libjami::exportable_callback<libjami::ConfigurationSignal::KnownDevicesChanged>( 110 3 : [&](const std::string& accountId, auto devices) { 111 3 : if (accountId == aliceId && devices.size() == 2) 112 1 : knownChanged = true; 113 3 : cv.notify_one(); 114 3 : })); 115 1 : libjami::registerSignalHandlers(confHandlers); 116 1 : auto alice2Id = jami::Manager::instance().addAccount(details); 117 1 : auto alice2Account = Manager::instance().getAccount<JamiAccount>(alice2Id); 118 5 : CPPUNIT_ASSERT(cv.wait_for(lk, std::chrono::seconds(60), [&] { return knownChanged; })); 119 1 : alice2Device = std::string(alice2Account->currentDeviceId()); 120 1 : aliceAccount->revokeDevice(alice2Device); 121 2 : CPPUNIT_ASSERT(cv.wait_for(lk, std::chrono::seconds(10), [&] { return deviceRevoked; })); 122 : 123 1 : std::remove("test.gz"); 124 1 : wait_for_removal_of(alice2Id); 125 1 : } 126 : 127 : void 128 1 : RevokeTest::testRevokeInvalidDevice() 129 : { 130 1 : auto aliceAccount = Manager::instance().getAccount<JamiAccount>(aliceId); 131 : 132 1 : std::mutex mtx; 133 1 : std::unique_lock lk {mtx}; 134 1 : std::condition_variable cv; 135 1 : std::map<std::string, std::shared_ptr<libjami::CallbackWrapperBase>> confHandlers; 136 1 : auto revokeFailed = false; 137 1 : confHandlers.insert( 138 2 : libjami::exportable_callback<libjami::ConfigurationSignal::DeviceRevocationEnded>( 139 1 : [&](const std::string& accountId, const std::string& deviceId, int status) { 140 1 : if (accountId == aliceId && deviceId == "foo" && status == 2) 141 1 : revokeFailed = true; 142 1 : cv.notify_one(); 143 1 : })); 144 1 : libjami::registerSignalHandlers(confHandlers); 145 1 : aliceAccount->revokeDevice("foo"); 146 2 : CPPUNIT_ASSERT(cv.wait_for(lk, std::chrono::seconds(10), [&] { return revokeFailed; })); 147 1 : } 148 : 149 : } // namespace test 150 : } // namespace jami 151 : 152 1 : RING_TEST_RUNNER(jami::test::RevokeTest::name())